This question already has answers here:
Casting variables in Java
(5 answers)
Closed 5 years ago.
I have to get an ImageView from a GridPane.
I use this code, but it is for Node, while I'm trying to change an Image in an ImageView (inside GridPane).
private Node getNodeFromGridPane(GridPane gridPane, int col, int row) {
for (Node node : gridPane.getChildren()) {
if (GridPane.getColumnIndex(node) == col && GridPane.getRowIndex(node) == row) {
System.out.println(node);
return node;
}
}
return null;
}
Is there a solution?
I already searched to lots of posts, but there is not this problem solved.
Thank you
On caller side you may do the next:
final Node foundNode = getNodeFromGridPane(gridPane, col, row);
if (foundNode instanceof ImageView) {
//do something
}
instanceof will care for both ImageView and null.
Related
Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 10 days ago.
Improve this question
I have TableView and my purpose is to have just one row at all [not included the col's title for each col]. And in every cell in the first row. I'll have ProgressIndicator.
Now, my purpose is everytime someone presses 'Add' it'll go to the OnAddButtonPressed function action and will add new col and in the first row in this specific col was just added a new progressIndicator will be added.
In my code right now, what is happening is everytime someone presses on 'ADD' what happens is all the ProgressIndicator were from earlier are moving to the new col and the num of rows gets incremented and all of the ProgressIndicator from the earalier columns gets removed and being "pushed" one by one to the new col.
#FXML
private void OnAddButtonPressed(ActionEvent event) {
int currentCPUTimeRequestedInteger;
String currentCPUTimeRequested = this.addTextField.getText();
if(currentCPUTimeRequested.isEmpty() || currentCPUTimeRequested.length() > 1 || !Character.isDigit(currentCPUTimeRequested.toCharArray()[0]) || currentCPUTimeRequested.toCharArray()[0] == '0')
{
PopAddButtonError();
return;
}
if(m_NumOfCols == MAX_NUM_OF_COLS - 1)
{
this.addButton.setDisable(true);
this.addTextField.setDisable(true);
this.enterCPUTimeLabel.setDisable(true);
}
if(firstTimePressedAdd == false)
{
this.firstTimePressedAdd = true;
this.startButton.setDisable(false);
this.listOfProcesses = new LinkedList<Process>();
}
currentCPUTimeRequestedInteger = Integer.parseInt(currentCPUTimeRequested);
this.addTextField.setText("");
AddNewColToTable(currentCPUTimeRequestedInteger);
}
private void AddNewColToTable(int CPUTimeRequested)
{
Process newProcess = new Process(CPUTimeRequested);
this.listOfProcesses.add(newProcess);
TableColumn newCol = new TableColumn("P" + newProcess.GetId());
newCol.setCellValueFactory(new PropertyValueFactory<Process, String>("progressIndicator"));
ObservableList<Process> data = FXCollections.observableArrayList();
data.add(newProcess);
this.tableOfProcesses.getColumns().add(newCol);
this.tableOfProcesses.getItems().addAll(data);
this.tableOfProcesses.refresh();
this.m_NumOfCols++;
}
My purpose is to have it the next way like in this photo:
enter image description here
Thank you for your help!
Treating this as an XY problem.
Here's how the sample image can mostly be achieved via an HBox:
class Progresses : Application() {
private var counter: Int = 0
override fun start(primaryStage: Stage) {
primaryStage.scene = Scene(createContent())
primaryStage.show()
}
private fun createContent(): Region = BorderPane().apply {
val hBox = HBox(20.0)
bottom = createButton(hBox)
center = hBox
padding = Insets(20.0)
minWidth = 400.0
minHeight = 150.0
}
private fun createButton(targetPane: Pane) = buttonOf("New Progress") { buttonAction(targetPane) }
private fun buttonAction(targetPane: Pane) {
targetPane.children += Label("P${counter++}").apply {
contentDisplay = ContentDisplay.BOTTOM
graphic = ProgressIndicator().apply {
progress = -1.0
object : AnimationTimer() {
var count = 0
override fun handle(now: Long) {
progress = (count++ / 5000.0).toDouble()
}
}.start()
}
}
}
}
fun main() = Application.launch(Progresses::class.java)
It's Kotlin, but you should be able to figure it out. It looks like this:
If the column heading styling is really required, you can style the Labels to give the same look and feel, or divide it into a VBox if that makes it easier.
This question already has answers here:
JavaFX print tableview on multiple pages
(3 answers)
Print contents of JavaFx TableView
(4 answers)
Closed 5 years ago.
I need help rating printing. in fact I would like to print all the contents of my tableview but the following code that I made prints that the data that appeared on the screen the others below do not appear.
printTestButton.setOnAction(new EventHandler<ActionEvent>() {
public void handle(ActionEvent e){
Printer printer = Printer.getDefaultPrinter();
Stage dialogStage = new Stage(StageStyle.DECORATED);
PrinterJob job = PrinterJob.createPrinterJob(printer);
if (job != null) {
boolean showDialog =job.showPrintDialog(printTestButton.getScene().getWindow());
// boolean showDialog = job.showPageSetupDialog(dialogStage);
if (showDialog) {
tableview.setScaleX(0.50);
tableview.setScaleY(0.60);
tableview.setTranslateX(-210);
tableview.setTranslateY(-80);
boolean success = job.printPage(tableview);
if (success) {
job.endJob();
}
tableview.setTranslateX(0);
tableview.setTranslateY(0);
tableview.setScaleX(1.0);
tableview.setScaleY(1.0);
}
}
}
});
This question already has answers here:
What is a NullPointerException, and how do I fix it?
(12 answers)
JavaFX show image near string in listview [closed]
(1 answer)
Closed 6 years ago.
#FXML
private TableColumn<Backup, Image>columnSucces;
columnSuccess.setCellValueFactory(new PropertyValueFactory<Backup, Image>("image"));
columnSucces.setCellFactory(new Callback<TableColumn<Backup, Image>, TableCell<Backup,Image>>(){
#Override
public TableCell<Backup, Image> call(TableColumn<Backup, Image> arg0) {
final ImageView imageview = new ImageView();
imageview.setFitHeight(50);
imageview.setFitWidth(50);
//Set up the Table
TableCell<Backup, Image> cell = new TableCell<Backup, Image>() {
public void updateItem(Backup item, boolean empty) {
if (item != null) {
imageview.setImage(new Image("x-mark-small.png"));
}
}
};
cell.setGraphic(imageView);
return cell;
}
});
I got nullpointerexception error when i am trying to add an image into a column for a table view. I cant understand where is my problem.
#edit. I have solved nullpointerexception, but now my image does not appear in the table column.
I received an warning that my updateItem method is never used.
I need to add a shape into a specific cell (middle centered one) in my GridPane.
This is how cells (StackPane) are made in my GridPane:
private StackPane createCell() {
StackPane cell = new StackPane();
cell.getStyleClass().add("cell");
return cell;
}
I have tried to get the centered cell with this piece of method:
private Node getCenteredNodeGridPane(GridPane gridPane, int col, int row) {
for (Node node : gridPane.getChildren()) {
if (GridPane.getColumnIndex(node) == col/2 && GridPane.getRowIndex(node) == row/2) {
return node;
}
}
return null;
}
And then, get the node:
Node centeredNode = getCenteredNodeGridPane(grid, 20, 20);
centeredNode ...... ??????
But i have no access to the actual StackPane of this node.
I need something like,
centeredNode.getChildren().add(shape);
Assuming you only add StackPanes as child nodes of the grid pane, you just need to cast the result:
StackPane centeredNode = (StackPane) getCenteredNodeGridPane(grid, 20, 20);
Depending on your exact requirements, you could of course do this in your getCenteredNodeGridPane method, and add type checking:
private StackPane getCenteredNodeGridPane(GridPane gridPane, int col, int row) {
for (Node node : gridPane.getChildren()) {
if (node instanceof StackPane
&& GridPane.getColumnIndex(node) == col/2
&& GridPane.getRowIndex(node) == row/2) {
return (StackPane) node;
}
}
return null;
}
I am attempting to create a "draggable" histogram UI with JavaFX. I have a ScrollPane containing a GridPane with 1 column and lots of rows. In each row is an HBox containing a label. Every 10 rows, there is also an HBox containing a Line.
I tried to make the HBoxes containing lines draggable by setting onMousePressed, onMouseDragged, and onMouseReleased event handlers (shown below). It works if I drag and release an hbox-line above its starting point - it ends up in whatever grid row I put it in, and I can click and drag it again. However, if I drag and release a line below its starting point, I can't get any more mouseEvents for that hBox. I tried adding log statements everywhere, nothing. I tried setting onMouseOver, it also was not fired.
Why would moving an hbox around the grid like this work for dragging up but not down?
lineContainer.setOnMousePressed(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent mouseEvent) {
EventTarget target = mouseEvent.getTarget();
lastY = mouseEvent.getSceneY();
}
});
lineContainer.setOnMouseDragged(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent mouseEvent) {
Node target = (Node) mouseEvent.getTarget();
HBox hBox = null;
if (target instanceof HBox) {
hBox = (HBox) target;
}
else if (target instanceof Line) {
hBox = (HBox) target.getParent();
}
else { //should never happen
log.info("target not hbox or line: " + target.getClass());
}
if (mouseEvent.getSceneY() <= (lastY - 15)) {
int row = GridPane.getRowIndex(hBox);
GridPane.setRowIndex(hBox, --row);
lastY = mouseEvent.getSceneY();
lastRow = row - 1;
} else if (mouseEvent.getSceneY() >= (lastY + 15)) {
int row = GridPane.getRowIndex(hBox);
GridPane.setRowIndex(hBox, ++row);
lastRow = row - 1;
lastY = mouseEvent.getSceneY();
}
}
});
lineContainer.setOnMouseReleased(new EventHandler<MouseEvent>() {
#Override
public void handle(MouseEvent mouseEvent) {
Node tar = (Node) mouseEvent.getTarget();
HBox hBox = null;
if (tar instanceof HBox) {
hBox = (HBox) tar;
}
else if (tar instanceof Line && tar.getParent() instanceof HBox) {
hBox = (HBox) tar.getParent();
}
else { //should never happen
log.info(mouseEvent.getTarget().getClass().toString());
}
}
});
UPDATE: I managed to get it working by creating a new HBox, resetting the onMouse... handlers, and copying its children every time the mouse is released. But I still don't know what was causing the original issue...
The following isn't a direct solution for you, but I wanted to say I have a similar problem and share my observations.
My application allows dragging in both axes (X, Y). All I've been able to figure out that some invisible element is 'obscuring' the MouseEvent hitbox. Testing it using an 'MS minesweeper' approach, shows this interfering area to extend from coords (0,0) of the root to (maxX,maxY) of another Node I have in the scene which is a layer above.
My problem was solved by changing z-order of Parent objects (let's call them layers) containing the Nodes that didn't receive their MouseEvents.
JavaFX MouseEvent doc explains that it is only the top level node which receives the event:
https://docs.oracle.com/javafx/2/api/javafx/scene/input/MouseEvent.html
Also look at the pickOnBounds property: JavaFX: How to make a Node partially mouse transparent?