## Step 1: Set up your project * Use Java 11 or higher (for built-in HttpClient) * Add **Gson** to your build: * If using Maven or Gradle, add Gson as explained before. * If plain, download gson JAR and add it to classpath. * Create your package, e.g., `mcmanage`. --- ## Step 2: Create ServerLocation class ```java package mcmanage; public class ServerLocation { public String name; public String ip; public int port; public ServerLocation(String name, String ip, int port) { this.name = name; this.ip = ip; this.port = port; } @Override public String toString() { return name + " (" + ip + ":" + port + ")"; } } ``` --- ## Step 3: Create JSON utility to load/save server locations ```java package mcmanage; import com.google.gson.Gson; import com.google.gson.reflect.TypeToken; import java.io.*; import java.lang.reflect.Type; import java.util.ArrayList; import java.util.List; public class ServerLocationStorage { private static final String FILE = "servers.json"; public static List load() { File file = new File(FILE); if (!file.exists()) { return new ArrayList<>(); } try (Reader reader = new FileReader(file)) { Gson gson = new Gson(); Type listType = new TypeToken>(){}.getType(); return gson.fromJson(reader, listType); } catch (IOException e) { e.printStackTrace(); return new ArrayList<>(); } } public static void save(List servers) { try (Writer writer = new FileWriter(FILE)) { Gson gson = new Gson(); gson.toJson(servers, writer); } catch (IOException e) { e.printStackTrace(); } } } ``` --- ## Step 4: Create PaperAPI client to fetch versions ```java package mcmanage; import com.google.gson.*; import java.io.IOException; import java.net.URI; import java.net.http.*; import java.util.ArrayList; import java.util.List; public class PaperAPIClient { private static final String API_URL = "https://api.papermc.io/v2/projects/paper"; public static List fetchPaperVersions() throws IOException, InterruptedException { HttpClient client = HttpClient.newHttpClient(); HttpRequest request = HttpRequest.newBuilder() .uri(URI.create(API_URL)) .GET() .build(); HttpResponse response = client.send(request, HttpResponse.BodyHandlers.ofString()); List versions = new ArrayList<>(); if (response.statusCode() == 200) { JsonObject json = JsonParser.parseString(response.body()).getAsJsonObject(); JsonArray versionsJson = json.getAsJsonArray("versions"); for (JsonElement v : versionsJson) { versions.add(v.getAsString()); } } return versions; } } ``` --- ## Step 5: Build the Swing GUI ```java package mcmanage; import javax.swing.*; import java.awt.*; import java.awt.event.*; import java.util.List; import java.util.concurrent.ExecutionException; public class ServerManagerUI extends JFrame { private DefaultListModel serverListModel = new DefaultListModel<>(); private JList serverList = new JList<>(serverListModel); private JTextField nameField = new JTextField(15); private JTextField ipField = new JTextField(15); private JTextField portField = new JTextField(5); private JButton addButton = new JButton("Add Server"); private JButton saveButton = new JButton("Save Servers"); private JButton fetchVersionsButton = new JButton("Fetch Paper Versions"); private JComboBox versionsComboBox = new JComboBox<>(); public ServerManagerUI() { super("Minecraft Server Manager"); setLayout(new BorderLayout()); // Left panel - list of servers JPanel leftPanel = new JPanel(new BorderLayout()); leftPanel.add(new JLabel("Saved Servers:"), BorderLayout.NORTH); leftPanel.add(new JScrollPane(serverList), BorderLayout.CENTER); // Right panel - input and buttons JPanel rightPanel = new JPanel(); rightPanel.setLayout(new BoxLayout(rightPanel, BoxLayout.Y_AXIS)); rightPanel.add(new JLabel("Name:")); rightPanel.add(nameField); rightPanel.add(new JLabel("IP Address:")); rightPanel.add(ipField); rightPanel.add(new JLabel("Port:")); rightPanel.add(portField); rightPanel.add(addButton); rightPanel.add(saveButton); rightPanel.add(new JLabel("Paper Versions:")); rightPanel.add(versionsComboBox); rightPanel.add(fetchVersionsButton); add(leftPanel, BorderLayout.CENTER); add(rightPanel, BorderLayout.EAST); // Load saved servers List savedServers = ServerLocationStorage.load(); savedServers.forEach(serverListModel::addElement); // Button listeners addButton.addActionListener(e -> addServer()); saveButton.addActionListener(e -> saveServers()); fetchVersionsButton.addActionListener(e -> fetchVersions()); setDefaultCloseOperation(EXIT_ON_CLOSE); setSize(600, 400); setLocationRelativeTo(null); setVisible(true); } private void addServer() { String name = nameField.getText().trim(); String ip = ipField.getText().trim(); String portStr = portField.getText().trim(); if (name.isEmpty() || ip.isEmpty() || portStr.isEmpty()) { JOptionPane.showMessageDialog(this, "Please fill all fields", "Input Error", JOptionPane.ERROR_MESSAGE); return; } int port; try { port = Integer.parseInt(portStr); } catch (NumberFormatException ex) { JOptionPane.showMessageDialog(this, "Invalid port number", "Input Error", JOptionPane.ERROR_MESSAGE); return; } ServerLocation server = new ServerLocation(name, ip, port); serverListModel.addElement(server); nameField.setText(""); ipField.setText(""); portField.setText(""); } private void saveServers() { List servers = serverListModel.elements().asIterator().toList(); ServerLocationStorage.save(servers); JOptionPane.showMessageDialog(this, "Servers saved!"); } private void fetchVersions() { fetchVersionsButton.setEnabled(false); versionsComboBox.removeAllItems(); SwingWorker, Void> worker = new SwingWorker<>() { @Override protected List doInBackground() throws Exception { return PaperAPIClient.fetchPaperVersions(); } @Override protected void done() { try { List versions = get(); versions.forEach(versionsComboBox::addItem); } catch (InterruptedException | ExecutionException e) { JOptionPane.showMessageDialog(ServerManagerUI.this, "Failed to fetch versions", "Error", JOptionPane.ERROR_MESSAGE); } finally { fetchVersionsButton.setEnabled(true); } } }; worker.execute(); } public static void main(String[] args) { SwingUtilities.invokeLater(ServerManagerUI::new); } } ``` --- ## Step 6: Run & test * Launch your `ServerManagerUI` main class. * Add servers manually and save them. * Click “Fetch Paper Versions” to load versions from Paper API. * The versions appear in the combo box dynamically. --- ## Summary * You have JSON save/load with Gson. * You fetch Paper versions dynamically using Java 11 HttpClient. * You use Swing for a simple GUI to manage your servers and versions. ---