Привет, я работаю над личным проектом и пытаюсь визуализировать некоторые изображения из папки ресурсов в свою игровую сцену в Javafx, пользователь отправляет четыре имени карты, разделенные запятыми, и я пытаюсь использовать эти значения для отображения соответствующих изображение на экран. При попытке загрузить изображение либо получаю ошибку нулевой ссылки, либо программа просто зависает.
public class Main extends Application implements EventHandler {
// History area for past picks
TextArea historyTextArea = new TextArea();
Button startButton; // Declare the button to access it in the handle method
// Add this line to declare the HBox for card images
private final HBox cardImagesBox = new HBox(10);
private final CardListManager cardListManager = new CardListManager(); // Instantiate CardListManager
private Label messageLabel; // Declare the message label at class levle, so it can be accessible by all methods
Helper helpMethodsObj = new Helper();
public static void main(String[] args) {
launch(args);
}
@Override
public void start(Stage primaryStage) {
// Set stage title
primaryStage.setTitle("The Art Dealer Game");
// Introduction text
Text introText = new Text("Welcome to \"The Art Dealer\" Game!\n" +
"Engage in a strategic round of card selection against the Art Dealer.\n\n" +
"How It Works:\n" +
"- Select cards one at a time to create a set of four.\n" +
"- The Art Dealer will only choose red cards.\n\n" +
"Rules:\n" +
"- Each card must be unique per round.\n" +
"- Select 'Start' to begin the game!");
introText.setTextAlignment(TextAlignment.CENTER);
introText.setStyle("-fx-font-size: 20; -fx-padding: 20;");
// Create the start button
startButton = new Button("Start");
startButton.setOnAction(this); // 'this' refers to the current instance which is an EventHandler
// Add button and text to the layout
StackPane layout = new StackPane();
layout.getChildren().addAll(introText, startButton);
StackPane.setAlignment(startButton, javafx.geometry.Pos.BOTTOM_CENTER);
StackPane.setAlignment(introText, javafx.geometry.Pos.CENTER);
// Set padding for the start button
StackPane.setMargin(startButton, new javafx.geometry.Insets(50));
historyTextArea = new TextArea();
// Create scene with layout
Scene introScene = new Scene(layout, 1500, 900);
primaryStage.setScene(introScene);
primaryStage.show();
}
private void goToGameScene(Stage stage) {
// Initialize the message label
messageLabel = new Label();
messageLabel.setStyle("-fx-font-size: 16;");
// Root layout
VBox rootLayout = new VBox(20);
rootLayout.setAlignment(javafx.geometry.Pos.TOP_CENTER);
rootLayout.setPadding(new javafx.geometry.Insets(20, 50, 20, 50)); // Add padding around the VBox
rootLayout.getChildren().add(messageLabel);
// Placeholder for card images
cardImagesBox.setAlignment(javafx.geometry.Pos.CENTER);
// Input field for user card picks
TextField cardInputField = new TextField();
cardInputField.setPromptText("Enter cards separated by commas");
cardInputField.setMaxWidth(300); // Set the maximum width for the text field
historyTextArea.setEditable(false);
historyTextArea.setMaxWidth(600); // Set maximum width
historyTextArea.setPrefHeight(200); // Set the preferred height
// ScrollPane to hold the history TextArea and provide scrolling
ScrollPane historyScrollPane = new ScrollPane(historyTextArea);
historyScrollPane.setHbarPolicy(ScrollPane.ScrollBarPolicy.AS_NEEDED);
historyScrollPane.setVbarPolicy(ScrollPane.ScrollBarPolicy.AS_NEEDED);
historyScrollPane.setMaxWidth(600); // Match width with the history text area
historyScrollPane.setPrefHeight(200); // Set the height
// Button for submitting card picks
Button submitButton = new Button("Submit Picks");
List cardList = cardListManager.createCardList();
submitButton.setOnAction(event -> {
String userInput = cardInputField.getText();
String[] cardCodes = userInput.split(",");// Split by comma
//check to make sure user put exactly 4 choices in
if (cardCodes.length != 4) {
messageLabel.setText("Please pick exactly four cards, separated by comma's (3H,4C,10H,9D).");
return; // Exit the event handler
}
List invalidCards = new ArrayList();
Set seenCards = new HashSet(); // use Set to track cards seen, since Sets only allow unique values
boolean hasDups = false;
for (String cardCode : cardCodes) {
cardCode = cardCode.trim().toUpperCase(); //trim and set to all upper for consistency
if (!seenCards.add(cardCode)) { // if the set already contains the card it will return false when add() is called.
hasDups = true;
break; //exit since dup is present.
}
if (!cardList.contains(cardCode)) {
invalidCards.add(cardCode);
}
}
if (hasDups) {
messageLabel.setText("Duplicate card detected. Each card must be unique.");
} else if (!invalidCards.isEmpty()) {
messageLabel.setText("Invalid card(s): " + String.join(", ", invalidCards));
} else {
messageLabel.setText("Submission Validated. All input cards are valid.");
// Update the history TextArea if all inputs are valid
historyTextArea.appendText(userInput + "\n");
updateHistory(userInput);//add to text file
loadImages(cardCodes); // Load and display images
}
// cardImagesBox.getChildren().clear(); // Clear previous card images
// Clear the input field
cardInputField.clear();
});
// VBox to hold the card input field and the submit button
VBox inputBox = new VBox(10, new Text("Input four cards:"), cardInputField, submitButton);
inputBox.setAlignment(javafx.geometry.Pos.CENTER);
// VBox to hold the history area
VBox historyBox = new VBox(10, new Text("History:"), historyScrollPane);
historyBox.setAlignment(javafx.geometry.Pos.CENTER);
// Combine input and history into a single layout
VBox combinedInputHistoryLayout = new VBox(20, inputBox, historyBox);
combinedInputHistoryLayout.setAlignment(javafx.geometry.Pos.CENTER);
// Add all components to the root layout
rootLayout.getChildren().addAll(cardImagesBox, combinedInputHistoryLayout);
// Create a new scene with the root layout
Scene gameScene = new Scene(rootLayout, 1500, 900);
stage.setScene(gameScene);
stage.show();
}
// Method to update the history TextArea with the user's input
private void updateHistory(String userInput) {
try (FileWriter writer = new FileWriter("CardsDealt.txt", true);
FileWriter writerIn = new FileWriter("in.txt", true)) {
writer.append(helpMethodsObj.getCurrentDateString()).append("\n");
writerIn.append(userInput).append("\n");
} catch (IOException e) {
e.printStackTrace();
}
}
//resources resources
private void loadImages(String[] cardCodes) {
cardImagesBox.getChildren().clear(); // Clear previous card images
System.out.println(System.getProperty("java.class.path"));
for (String cardCode : cardCodes) {
final String code = cardCode.toUpperCase().trim();
String imagePath = "resources/" + code + ".png"; // make sure images are under src/main/resources/images
Image image = new Image(imagePath);
InputStream is = getClass().getResourceAsStream(imagePath);
if (is == null) {
System.out.println("The file does not exist: " + imagePath);
continue; // Skip this iteration if the image does not exist
}
//Image image = new Image(Objects.requireNonNull(getClass().getResourceAsStream(imagePath)));
ImageView imageView = new ImageView(image);
cardImagesBox.getChildren().add(imageView);
}
}
private void showAlert(String title, String content, Alert.AlertType alertType) {
Alert alert = new Alert(alertType);
alert.setTitle(title);
alert.setHeaderText(null);
alert.setContentText(content);
alert.showAndWait();
}
@Override
public void handle(ActionEvent actionEvent) {
if (actionEvent.getSource() == startButton) {
Stage stage = (Stage) startButton.getScene().getWindow();
goToGameScene(stage); // Switch to the game scene
}
}
}
Подробнее здесь: https://stackoverflow.com/questions/781 ... load-image