Highscore Eintrag für Name hinzugefügt

continueCode
Vickvick2002 2025-01-05 16:22:30 +01:00
parent eb30f5cd13
commit f7868e042f
4 changed files with 153 additions and 96 deletions

View File

@ -9,8 +9,6 @@ import PR2.HitoriSpiel.Utils.Setup;
import javax.swing.*;
import java.awt.*;
import java.io.FileWriter;
import java.io.IOException;
public class GameBoard extends JPanel {
private final HitoriBoard board;
@ -25,11 +23,8 @@ public class GameBoard extends JPanel {
this.board = board;
setLayout(new BorderLayout());
// Timer-Label oben hinzufügen
timerLabel = new JLabel("Zeit: 0 Sekunden");
timerLabel.setHorizontalAlignment(SwingConstants.CENTER);
Setup.styleLabel(timerLabel);
add(timerLabel, BorderLayout.NORTH);
// Timer-Label hinzufügen
initializeTimerLabel();
// Timer starten
startTimer();
@ -43,6 +38,13 @@ public class GameBoard extends JPanel {
add(controlPanel, BorderLayout.SOUTH);
}
private void initializeTimerLabel() {
timerLabel = new JLabel("Zeit: 0 Sekunden");
timerLabel.setHorizontalAlignment(SwingConstants.CENTER);
Setup.styleLabel(timerLabel);
add(timerLabel, BorderLayout.NORTH);
}
private void startTimer() {
startTime = System.currentTimeMillis();
timer = new Timer(1000, e -> {
@ -61,13 +63,25 @@ public class GameBoard extends JPanel {
private JPanel createControlPanel() {
JPanel controlPanel = new JPanel();
controlPanel.add(createResetButton());
controlPanel.add(createUndoButton());
controlPanel.add(createRedoButton());
controlPanel.add(createValidateButton());
controlPanel.add(createPauseButton());
return controlPanel;
}
private JButton createResetButton() {
JButton resetButton = Setup.createGameBoardButton("Zurücksetzen", 150, 30);
resetButton.addActionListener(e -> {
saveStateForUndo();
resetBoard();
//refreshBoard();
});
return resetButton;
}
private JButton createUndoButton() {
JButton undoButton = Setup.createGameBoardButton("Undo", 80, 30);
undoButton.addActionListener(e -> {
int[][] previousState = stateManager.undo(board.getNumbers());
@ -78,49 +92,64 @@ public class GameBoard extends JPanel {
JOptionPane.showMessageDialog(this, "Kein Zustand zum Zurücksetzen vorhanden.", "Undo", JOptionPane.INFORMATION_MESSAGE);
}
});
return undoButton;
}
private JButton createRedoButton() {
JButton redoButton = Setup.createGameBoardButton("Redo", 80, 30);
redoButton.addActionListener(e -> {
int[][] nextState = stateManager.redo(board.getNumbers());
if (nextState != null) {
board.setNumbers(nextState);
refreshBoard();
updateBoard();
} else {
JOptionPane.showMessageDialog(this, "Kein Zustand zum Wiederholen vorhanden.", "Redo", JOptionPane.INFORMATION_MESSAGE);
}
});
return redoButton;
}
private JButton createValidateButton() {
JButton validateButton = Setup.createGameBoardButton("Lösen", 80, 30);
validateButton.addActionListener(e -> {
if (validateCurrentBoard()) {
stopTimer();
JOptionPane.showMessageDialog(this, "Das Spielfeld ist korrekt gelöst!", "Erfolg", JOptionPane.INFORMATION_MESSAGE);
handleHighscore();
} else {
JOptionPane.showMessageDialog(this, "Das Spielfeld enthält Fehler!", "Fehler", JOptionPane.ERROR_MESSAGE);
}
});
return validateButton;
}
private JButton createPauseButton() {
JButton pauseButton = Setup.createGameBoardButton("Pause", 80, 30);
pauseButton.addActionListener(e -> {
stopTimer();
showPauseMenu();
});
controlPanel.add(resetButton);
controlPanel.add(undoButton);
controlPanel.add(redoButton);
controlPanel.add(validateButton);
controlPanel.add(pauseButton);
return controlPanel;
return pauseButton;
}
public boolean validateCurrentBoard() {
HitoriValidator validator = new HitoriValidator(board);
return validator.validateBoard(board.getSolutionCoordinates());
}
private void handleHighscore() {
int elapsedTime = (int) ((System.currentTimeMillis() - startTime) / 1000);
String boardName = board.getBoardName();
HighscoreManager manager = new HighscoreManager();
boolean isNewHighscore = manager.isNewHighscore(elapsedTime, boardName);
if (isNewHighscore) {
addHighscore(elapsedTime, boardName);
} else {
JOptionPane.showMessageDialog(this, "Das Spielfeld ist korrekt gelöst!", "Erfolg", JOptionPane.INFORMATION_MESSAGE);
}
}
private void showPauseMenu() {
PauseMenu pauseMenu = new PauseMenu(
(JFrame) SwingUtilities.getWindowAncestor(this),
@ -146,30 +175,27 @@ public class GameBoard extends JPanel {
System.err.println("Ungültige Zelle! Der Zustand kann nicht geändert werden.");
return;
}
if (cell.getState() == HitoriCell.CellState.GRAY) {
cell.setState(HitoriCell.CellState.BLACK);
} else if (cell.getState() == HitoriCell.CellState.BLACK) {
cell.setState(HitoriCell.CellState.WHITE);
} else {
cell.setState(HitoriCell.CellState.GRAY);
switch (cell.getState()) {
case GRAY -> cell.setState(HitoriCell.CellState.BLACK);
case BLACK -> cell.setState(HitoriCell.CellState.WHITE);
case WHITE -> cell.setState(HitoriCell.CellState.GRAY);
}
}
private void updateButtonState(JButton button, HitoriCell cell) {
switch (cell.getState()) {
case GRAY:
case GRAY -> {
button.setBackground(Color.LIGHT_GRAY);
button.setText(String.valueOf(cell.getNumber()));
break;
case BLACK:
}
case BLACK -> {
button.setBackground(Color.BLACK);
button.setForeground(Color.WHITE);
break;
case WHITE:
}
case WHITE -> {
button.setBackground(Color.WHITE);
button.setText(String.valueOf(cell.getNumber()));
button.setForeground(Color.BLACK);
break;
}
}
}
@ -177,41 +203,23 @@ public class GameBoard extends JPanel {
stateManager.saveState(board.getNumbers());
}
private void addHighscore() {
private void addHighscore(int elapsedTime, String boardName) {
String playerName = JOptionPane.showInputDialog(this,
"Bitte geben Sie Ihren Namen ein:",
"Neuer Highscore! Bitte Namen eingeben:",
"Highscore speichern",
JOptionPane.PLAIN_MESSAGE);
if (playerName == null || playerName.trim().isEmpty()) {
JOptionPane.showMessageDialog(this,
"Highscore wurde nicht gespeichert. Kein Name eingegeben.",
"Info",
JOptionPane.INFORMATION_MESSAGE);
return;
}
if (playerName == null || playerName.trim().isEmpty()) return;
int elapsedTime = (int) ((System.currentTimeMillis() - startTime) / 1000);
HighscoreManager manager = new HighscoreManager();
manager.addHighscore(playerName, elapsedTime, boardName);
String boardName = board.getBoardName();
try {
HighscoreManager manager = new HighscoreManager();
manager.addHighscore(playerName, elapsedTime, boardName);
JOptionPane.showMessageDialog(this,
"Highscore erfolgreich gespeichert!",
"Erfolg",
JOptionPane.INFORMATION_MESSAGE);
} catch (Exception e) {
JOptionPane.showMessageDialog(this,
"Fehler beim Speichern des Highscores: " + e.getMessage(),
"Fehler",
JOptionPane.ERROR_MESSAGE);
}
JOptionPane.showMessageDialog(this,
"Highscore erfolgreich gespeichert!",
"Erfolg",
JOptionPane.INFORMATION_MESSAGE);
}
private void returnToMainMenu() {
/// Eltern-Frame abrufen
JFrame parentFrame = (JFrame) SwingUtilities.getWindowAncestor(this);
@ -240,10 +248,8 @@ public class GameBoard extends JPanel {
if (centerComponent != null) {
remove(centerComponent);
}
// Neues Spielfeld hinzufügen
add(createGamePanel(), BorderLayout.CENTER);
// Kontroll-Buttons (SOUTH) entfernen und neu hinzufügen
Component southComponent = layout.getLayoutComponent(BorderLayout.SOUTH);
if (southComponent != null) {
@ -251,7 +257,6 @@ public class GameBoard extends JPanel {
}
add(createControlPanel(), BorderLayout.SOUTH);
}
// Oberfläche aktualisieren
revalidate();
repaint();

View File

@ -6,7 +6,9 @@ import PR2.HitoriSpiel.Utils.Setup;
import javax.swing.table.DefaultTableModel;
import javax.swing.*;
import java.awt.*;
import java.util.Comparator;
import java.util.List;
import java.util.concurrent.atomic.AtomicInteger;
// aktueller Stand
public class HighscoreDialog extends JDialog {
@ -16,11 +18,11 @@ public class HighscoreDialog extends JDialog {
public HighscoreDialog(JFrame parentFrame) {
super(parentFrame, "Highscoreliste", true);
this.highscoreManager = new HighscoreManager();
setLayout(new BorderLayout());
setSize(500, 400);
setSize(600, 400);
setLocationRelativeTo(parentFrame);
this.highscoreManager = new HighscoreManager();
setLayout(new BorderLayout());
Setup.stylePanel((JPanel) getContentPane()); // Hintergrundfarbe setzen
JLabel titleLabel = new JLabel("Highscores", SwingConstants.CENTER);
@ -28,7 +30,7 @@ public class HighscoreDialog extends JDialog {
Setup.styleLabel(titleLabel); // Schriftstil setzen
add(titleLabel, BorderLayout.NORTH);
String[] columnNames = {"Name", "Punkte", "Spielfeld"};
String[] columnNames = {"Platz", "Name", "Zeit (Sek.)", "Spielfeld"};
tableModel = new DefaultTableModel(columnNames, 0);
JTable highscoreTable = new JTable(tableModel);
highscoreTable.setFillsViewportHeight(true);
@ -36,14 +38,34 @@ public class HighscoreDialog extends JDialog {
JScrollPane scrollPane = new JScrollPane(highscoreTable);
add(scrollPane, BorderLayout.CENTER);
// Schließen-Button
JButton closeButton = Setup.createButton("Schließen", 120, 40);
closeButton.setFont(new Font(closeButton.getFont().getName(), closeButton.getFont().getStyle(), 14)); // Schriftgröße ändern
closeButton.addActionListener(e -> dispose());
JPanel buttonPanel = new JPanel();
Setup.stylePanel(buttonPanel); // Hintergrundstil setzen
// Schließen-Button
JButton closeButton = Setup.createButton("Schließen", 200, 40);
closeButton.setFont(new Font(closeButton.getFont().getName(), closeButton.getFont().getStyle(), 18)); // Schriftgröße ändern
closeButton.addActionListener(e -> dispose());
buttonPanel.add(closeButton);
// Button zum Löschen aller Einträge
JButton clearButton = Setup.createButton("Einträge löschen", 200, 40);
clearButton.setFont(new Font(closeButton.getFont().getName(), closeButton.getFont().getStyle(), 18));
clearButton.addActionListener(e -> {
int confirmation = JOptionPane.showConfirmDialog(
this,
"Möchten Sie wirklich alle Highscores löschen?",
"Highscores löschen",
JOptionPane.YES_NO_OPTION
);
if (confirmation == JOptionPane.YES_OPTION) {
highscoreManager.clearHighscores();
loadHighscores(); // Tabelle aktualisieren
JOptionPane.showMessageDialog(this, "Alle Highscores wurden gelöscht.");
}
});
buttonPanel.add(clearButton);
Setup.stylePanel(buttonPanel); // Hintergrundstil setzen
add(buttonPanel, BorderLayout.SOUTH);
// Highscores laden
@ -54,13 +76,17 @@ public class HighscoreDialog extends JDialog {
tableModel.setRowCount(0); // Tabelle zurücksetzen
List<HighscoreManager.Highscore> highscores = highscoreManager.getHighscores();
highscores.stream()
.sorted((a, b) -> Integer.compare(b.getScore(), a.getScore())) // Sortierung: Höchste Punkte zuerst
.forEach(highscore -> tableModel.addRow(new Object[]{
highscore.getPlayerName(),
highscore.getScore(),
highscore.getBoardName()
}));
highscores.sort(Comparator.comparingInt(HighscoreManager.Highscore::getScore)); // Sortierung: Kürzeste Zeit zuerst
int rank = 1; // Platznummer
for (HighscoreManager.Highscore highscore : highscores) {
tableModel.addRow(new Object[]{
rank++, // Platznummer hochzählen
highscore.getPlayerName(), // Name des Spielers
highscore.getScore(), // Zeit in Sekunden
highscore.getBoardName() // Name des Spielfelds
});
}
}
public void refreshHighscores() {

View File

@ -19,17 +19,47 @@ public class HighscoreManager {
}
// Highscore hinzufügen
public synchronized void addHighscore(String playerName, int score, String boardName) {
public synchronized void addHighscore(String playerName, int time, String boardName) {
fileLock.lock();
try {
highscoreList.add(new Highscore(playerName, score, boardName));
highscoreList.sort(Comparator.comparingInt(Highscore::getScore).reversed()); // Sortierung absteigend
saveHighscores();
// Prüfe, ob es bereits Highscores für das Spielfeld gibt
boolean isShorterTime = highscoreList.stream()
.filter(highscore -> highscore.getBoardName().equals(boardName))
.allMatch(highscore -> time < highscore.getScore());
if (isShorterTime) {
// Entferne alle Highscores für das Spielfeld, die länger oder gleich sind
highscoreList.removeIf(highscore -> highscore.getBoardName().equals(boardName));
// Füge den neuen Highscore hinzu
highscoreList.add(new Highscore(playerName, time, boardName));
// Sortiere die Liste
highscoreList.sort(Comparator.comparingInt(Highscore::getScore)); // Kürzeste Zeit zuerst
saveHighscores();
} else {
System.out.println("Neuer Highscore ist nicht kürzer als die bestehenden Einträge.");
}
} finally {
fileLock.unlock();
}
}
// Neue Methode: Überprüfung, ob ein neuer Highscore erreicht wurde
public boolean isNewHighscore(int elapsedTime, String boardName) {
List<Highscore> highscores = getHighscores();
// Prüfen, ob das Board bereits einen Highscore-Eintrag hat
for (Highscore highscore : highscores) {
if (highscore.getBoardName().equals(boardName)) {
return elapsedTime < highscore.getScore(); // Neuer Highscore, wenn Zeit besser ist
}
}
// Wenn das Board keinen Highscore hat, ist dies der erste Eintrag
return true;
}
// Highscores laden
private void loadHighscores() {
fileLock.lock();
@ -68,17 +98,15 @@ public class HighscoreManager {
// Highscores abrufen
public List<Highscore> getHighscores() {
return Collections.unmodifiableList(highscoreList);
return new ArrayList<>(highscoreList); // Modifizierbare Kopie zurückgeben
}
// Alte Highscores bereinigen
public void cleanOldHighscores(int maxEntries) {
// Löscht alle Highscores
public void clearHighscores() {
fileLock.lock();
try {
if (highscoreList.size() > maxEntries) {
highscoreList.subList(maxEntries, highscoreList.size()).clear();
saveHighscores();
}
highscoreList.clear(); // Liste leeren
saveHighscores(); // Datei aktualisieren
} finally {
fileLock.unlock();
}
@ -107,7 +135,7 @@ public class HighscoreManager {
public String getBoardName() {
return boardName;
}
}
}

View File

@ -1,3 +1 @@
Name, Zeit (Sekunden), Spielfeld
NameTest, 123 Sekunden, Hitori4x4_leicht.csv
ame, Zeit (Sekunden), Spielfeld