javauser-interfacejavafxserverfxml

Error in updating client list in server UI FXML


I'm working on a simple client-server project. The function of it doesn't really matter because I'm having a problem with the client list in my server UI. It uses FXML and has a listView to list the clients IP address but it doesn't update when a new client is launched. I tried a bunch of methods to approach this but I would love some help here. I've given the codes below. If what I've provided is not sufficent please let me know and I'll update this post.

enter code herepackage chattingnetwork;

import javafx.application.Platform;
import javafx.scene.control.ListView;

import java.io.*;
import java.net.*;
import java.util.Date;

public class Server {

private static ListView<String> clientListView;

public static void startServer() {
    try {
        ServerSocket serverSocket = new ServerSocket(8000);
        System.out.println("Server started at " + new Date() + '\n');

        while (true) {
            Socket socket = serverSocket.accept();
            String clientIP = socket.getInetAddress().getHostAddress();

            System.out.println("Client connected: " + clientIP);

            Platform.runLater(() -> {
                if (clientListView != null) {
                    clientListView.getItems().add(clientIP);
                    System.out.println("Added client to ListView: " + clientIP);
                } else {
                    System.out.println("clientListView is not initialized");
                }
            });

            new Thread(new ClientHandler(socket)).start();
        }
    } catch (IOException e) {
        System.err.println("Error starting server: " + e.getMessage());
    }
}

public static void setClientListView(ListView<String> listView) {
    clientListView = listView;
    }
}

This is my server side code and when a new client is connected it does print out to the console a new client is connected but like I mentioned the ListView in the UI doesn't update. Here's my controller and the FXML codes:

package chattingnetwork;

import javafx.fxml.FXML;
import javafx.scene.control.ListView;

public class serverFXMLController {

    @FXML
    private ListView<String> clientListView;

    @FXML
    public void initialize() {
        System.out.println("Server UI initialized.");
        if (clientListView != null) {
            System.out.println("clientListView is initialized.");
            Server.setClientListView(clientListView);
        } else {
            System.out.println("clientListView is null.");
        }
    }
}

When a new client is connected "clientListView is initialized." is printed in the console. Here's the FXML file of the server UI:

<?xml version="1.0" encoding="UTF-8"?>

<?import javafx.scene.control.ListView?>
<?import javafx.scene.layout.AnchorPane?>

<AnchorPane xmlns="http://javafx.com/javafx/8.0.171" xmlns:fx="http://javafx.com/fxml/1">
    <ListView fx:id="clientListView" layoutX="14.0" layoutY="14.0" prefHeight="200.0" prefWidth="400.0"/>
</AnchorPane>

Solution

  • use ObservableList

    package chattingnetwork;
    
    import javafx.application.Platform;
    import javafx.collections.FXCollections;
    import javafx.collections.ObservableList;
    
    import java.io.*;
    import java.net.*;
    import java.util.Date;
    
    public class Server {
    
        private static ObservableList<String> clientList = FXCollections.observableArrayList();
    
        public static ObservableList<String> getClientList() {
            return clientList;
        }
    
        public static void startServer() {
            try {
                ServerSocket serverSocket = new ServerSocket(8000);
                System.out.println("Server started at " + new Date() + '\n');
    
                while (true) {
                    Socket socket = serverSocket.accept();
                    String clientIP = socket.getInetAddress().getHostAddress();
    
                    System.out.println("Client connected: " + clientIP);
    
                    Platform.runLater(() -> {
                        clientList.add(clientIP); // Add client to the ObservableList
                    });
    
                    new Thread(new ClientHandler(socket)).start();
                }
            } catch (IOException e) {
                System.err.println("Error starting server: " + e.getMessage());
            }
        }
    }
    
    

    and then

    package chattingnetwork;
    
    import javafx.fxml.FXML;
    import javafx.scene.control.ListView;
    
    public class serverFXMLController {
    
        @FXML
        private ListView<String> clientListView;
    
        @FXML
        public void initialize() {
            System.out.println("Server UI initialized.");
            if (clientListView != null) {
                System.out.println("clientListView is initialized.");
                clientListView.setItems(Server.getClientList()); // Bind the ObservableList to the ListView
            } else {
                System.out.println("clientListView is null.");
            }
        }
    }