Merge remote-tracking branch 'origin/gui' into gui

This commit is contained in:
Yvonne Schmidt 2024-11-29 05:16:44 +01:00
commit 1ccdea0c87
16 changed files with 416 additions and 169 deletions

View File

@ -7,15 +7,15 @@
package pp.monopoly.client;
import java.lang.System.Logger;
import java.util.List;
import com.jme3.input.controls.ActionListener;
import com.jme3.scene.Node;
import com.jme3.system.AppSettings;
import pp.monopoly.client.MonopolyAppState;
import pp.monopoly.client.gui.TestWorld;
import pp.monopoly.model.IntPoint;
import java.lang.System.Logger;
import java.lang.System.Logger.Level;
import pp.monopoly.client.gui.TestWorld;
import pp.monopoly.game.server.Player;
/**
* Represents the state responsible for managing the battle interface within the Battleship game.
@ -71,9 +71,14 @@ public class GameAppState extends MonopolyAppState {
* Creates the opponent's map view and adds a grid overlay to it.
*/
private void initializeGuiComponents() {
testWorld = new TestWorld(getApp());
// Abrufen der Spielerliste aus der ClientGameLogic
List<Player> players = getApp().getGameLogic().getPlayerHandler().getPlayers();
// Initialisiere TestWorld mit Spielern
testWorld = new TestWorld(getApp(), players);
testWorld.initializeScene();
}
/**
* Adds the initialized GUI components to the battle node.

View File

@ -7,6 +7,15 @@
package pp.monopoly.client;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.lang.System.Logger;
import java.lang.System.Logger.Level;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.logging.LogManager;
import com.jme3.app.DebugKeysAppState;
import com.jme3.app.SimpleApplication;
import com.jme3.app.StatsAppState;
@ -19,34 +28,24 @@ import com.jme3.input.controls.KeyTrigger;
import com.jme3.input.controls.MouseButtonTrigger;
import com.jme3.system.AppSettings;
import com.simsilica.lemur.GuiGlobals;
import com.simsilica.lemur.Label;
import com.simsilica.lemur.style.BaseStyles;
import pp.monopoly.client.gui.popups.*;
import pp.monopoly.game.client.MonopolyClient;
import pp.dialog.Dialog;
import pp.dialog.DialogBuilder;
import pp.dialog.DialogManager;
import pp.graphics.Draw;
import static pp.monopoly.Resources.lookup;
import pp.monopoly.client.gui.SettingsMenu;
import pp.monopoly.client.gui.StartMenu;
import pp.monopoly.client.gui.TestWorld;
import pp.monopoly.client.gui.popups.*;
import pp.monopoly.game.client.ClientGameLogic;
import pp.monopoly.game.client.MonopolyClient;
import pp.monopoly.game.client.ServerConnection;
import pp.monopoly.notification.ClientStateEvent;
import pp.monopoly.notification.GameEventListener;
import pp.monopoly.notification.InfoTextEvent;
import pp.monopoly.notification.Sound;
import pp.dialog.Dialog;
import pp.dialog.DialogBuilder;
import pp.dialog.DialogManager;
import pp.graphics.Draw;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.lang.System.Logger;
import java.lang.System.Logger.Level;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.logging.LogManager;
import static pp.monopoly.Resources.lookup;
/**
* The main class for the Battleship client application.
@ -131,9 +130,9 @@ public class MonopolyApp extends SimpleApplication implements MonopolyClient, Ga
private GateFieldCard gateField;
private BuyCard buyCard;
private LooserPopUp looserpopup;
private Bankrupt bankrupt;
private boolean isBuyCardPopupOpen = false;
private final ActionListener BListener = (name, isPressed, tpf) -> handleB(isPressed);
private final ActionListener TListener = (name, isPressed, tpf) -> handleT(isPressed);
private TestWorld testWorld;
static {
@ -269,24 +268,18 @@ public class MonopolyApp extends SimpleApplication implements MonopolyClient, Ga
inputManager.addMapping("B", new KeyTrigger(KeyInput.KEY_B));
inputManager.addListener(BListener, "B");
inputManager.addMapping("T", new KeyTrigger(KeyInput.KEY_T));
inputManager.addListener(TListener, "T");
}
//logik zum wechselnden erscheinen und verschwinden beim drücken von B //TODO süäter entfernen
private void handleB(boolean isPressed) {
if (isPressed) {
Dialog tmp = new SellHouse(this);
Dialog tmp = new Bankrupt(this);
tmp.open();
}
}
//logik zum wechselnden erscheinen und verschwinden beim drücken von B //TODO süäter entfernen
private void handleT(boolean isPressed) {
if (isPressed) {
testWorld = new TestWorld(this);
testWorld.initializeScene();
}
}

View File

@ -2,24 +2,19 @@ package pp.monopoly.client.gui;
import java.util.Set;
import com.jme3.app.Application;
import com.jme3.app.state.BaseAppState;
import com.jme3.material.Material;
import com.jme3.math.ColorRGBA;
import com.jme3.math.Vector3f;
import com.jme3.scene.Geometry;
import com.jme3.scene.shape.Quad;
import com.jme3.texture.Texture;
import com.simsilica.lemur.Axis;
import com.simsilica.lemur.Button;
import com.simsilica.lemur.Container;
import com.simsilica.lemur.Label;
import com.simsilica.lemur.Selector;
import com.simsilica.lemur.*;
import com.simsilica.lemur.component.QuadBackgroundComponent;
import com.simsilica.lemur.component.SpringGridLayout;
import com.simsilica.lemur.core.VersionedList;
import com.simsilica.lemur.core.VersionedReference;
import com.simsilica.lemur.style.ElementId;
import pp.dialog.Dialog;
import pp.monopoly.client.MonopolyApp;
import pp.monopoly.game.server.Player;
@ -37,6 +32,9 @@ public class ChoosePartner extends Dialog {
private Container lowerRightMenu;
private Geometry background;
private TradeHandler tradeHandler;
private VersionedReference<Set<Integer>> selectionRef; // Reference to track selector changes
private String lastSelected = ""; // To keep track of the last selected value
QuadBackgroundComponent translucentWhiteBackground =
new QuadBackgroundComponent(new ColorRGBA(1.0f, 1.0f, 1.0f, 0.5f));
@ -70,8 +68,6 @@ public class ChoosePartner extends Dialog {
// Add buttons
mainContainer.addChild(createButtonContainer());
addSelectionActionListener(playerSelector, this::onDropdownSelectionChanged);
// Attach main container to GUI node
app.getGuiNode().attachChild(mainContainer);
mainContainer.setLocalTranslation(
@ -79,6 +75,9 @@ public class ChoosePartner extends Dialog {
(app.getCamera().getHeight() + mainContainer.getPreferredSize().y) / 2,
4
);
// Initialize selection reference for tracking changes
selectionRef = playerSelector.getSelectionModel().createReference();
}
/**
@ -95,7 +94,7 @@ public class ChoosePartner extends Dialog {
for (Player player : app.getGameLogic().getPlayerHandler().getPlayers()) {
if (player.getId() != app.getId()) {
playerOptions.add(player.getName() + " (ID: "+player.getId()+")");
playerOptions.add(player.getName() + " (ID: " + player.getId() + ")");
}
}
@ -103,10 +102,14 @@ public class ChoosePartner extends Dialog {
dropdownContainer.addChild(playerSelector);
Vector3f dimens = dropdownContainer.getPreferredSize();
Vector3f dimens2 = playerSelector.getPopupContainer().getPreferredSize();
dimens2.setX( dimens.getX() );
playerSelector.getPopupContainer().setPreferredSize(new Vector3f(200,200,3));
playerSelector.setLocalTranslation(0,0,5);
onDropdownSelectionChanged(playerOptions.get(0));
dimens2.setX(dimens.getX());
playerSelector.getPopupContainer().setPreferredSize(new Vector3f(200, 200, 3));
playerSelector.setLocalTranslation(0, 0, 5);
// Set initial selection
if (!playerOptions.isEmpty()) {
onDropdownSelectionChanged(playerOptions.get(0));
}
return dropdownContainer;
}
@ -134,7 +137,6 @@ public class ChoosePartner extends Dialog {
lowerLeftMenu.setLocalTranslation(new Vector3f(120, 170, 5)); // Adjust X and Y to align with the bottom-left corner
app.getGuiNode().attachChild(lowerLeftMenu);
// "Bestätigen" button
lowerRightMenu = new Container();
confirmButton.setPreferredSize(new Vector3f(200, 60, 0));
@ -150,7 +152,6 @@ public class ChoosePartner extends Dialog {
lowerRightMenu.setLocalTranslation(new Vector3f(app.getCamera().getWidth() - 320, 170, 5)); // X: 220px from the right, Y: 50px above the bottom
app.getGuiNode().attachChild(lowerRightMenu);
return buttonContainer;
}
@ -183,7 +184,14 @@ public class ChoosePartner extends Dialog {
*/
@Override
public void update(float delta) {
// Periodic updates (if needed) can be implemented here
// Check if the selection has changed
if (selectionRef.update()) {
String selected = playerSelector.getSelectedItem();
if (!selected.equals(lastSelected)) {
lastSelected = selected;
onDropdownSelectionChanged(selected);
}
}
}
@Override
@ -196,42 +204,6 @@ public class ChoosePartner extends Dialog {
super.close();
}
/**
* Adds a custom action listener to the Selector.
*/
private void addSelectionActionListener(Selector<String> selector, SelectionActionListener<String> listener) {
VersionedReference<Set<Integer>> selectionRef = selector.getSelectionModel().createReference();
app.getStateManager().attach(new BaseAppState() {
@Override
public void update(float tpf) {
if (selectionRef.update()) {
String selected = selectionRef.get().toString();
listener.onSelectionChanged(selected);
}
}
@Override
protected void initialize(Application app) {
update(1);
}
@Override
protected void cleanup(Application app) {
}
@Override
protected void onEnable() {
}
@Override
protected void onDisable() {
}
});
}
/**
* Callback for when the dropdown selection changes.
*/
@ -241,23 +213,12 @@ public class ChoosePartner extends Dialog {
int idEnd = selected.indexOf(")", idStart); // Find end of the ID
String idStr = selected.substring(idStart, idEnd); // Extract the ID as a string
int playerId = Integer.parseInt(idStr); // Convert the ID to an integer
// Find the player by ID
Player selectedPlayer = app.getGameLogic().getPlayerHandler().getPlayerById(playerId);
if (selectedPlayer != null) {
tradeHandler.setReceiver(selectedPlayer); // Set the receiver in TradeHandler
}
}
/**
* Functional interface for a selection action listener.
*/
@FunctionalInterface
private interface SelectionActionListener<T> {
void onSelectionChanged(T selection);
}
}

View File

@ -2,18 +2,12 @@ package pp.monopoly.client.gui;
import java.util.List;
import com.jme3.material.Material;
import com.jme3.math.ColorRGBA;
import com.jme3.math.Vector3f;
import com.jme3.scene.Geometry;
import com.jme3.scene.shape.Box;
import com.jme3.texture.Texture;
import pp.monopoly.client.MonopolyApp;
import pp.monopoly.client.gui.popups.BuyCard;
import pp.monopoly.client.gui.popups.EventCard;
import pp.monopoly.client.gui.popups.FoodFieldCard;
import pp.monopoly.client.gui.popups.GateFieldCard;
import pp.monopoly.game.server.Player;
import pp.monopoly.model.fields.BuildingProperty;
import pp.monopoly.model.fields.FoodField;
import pp.monopoly.model.fields.GateField;
@ -24,90 +18,112 @@ import pp.monopoly.notification.GameEventListener;
import pp.monopoly.notification.PopUpEvent;
/**
* TestWorld zeigt eine einfache Szene mit einem texturierten Quadrat.
* Die Kamera wird durch den CameraController gesteuert.
* TestWorld zeigt eine einfache Szene mit Spielfeld und Spielfiguren.
*/
public class TestWorld implements GameEventListener{
public class TestWorld {
private final MonopolyApp app;
private CameraController cameraController; // Steuert die Kamera
private Toolbar toolbar;
private final List<Player> players; // Liste der Spieler, bereits aus GameStart geladen
private CameraController cameraController;
/**
* Konstruktor für TestWorld.
* Konstruktor für die TestWorld.
*
* @param app Die Hauptanwendung (MonopolyApp)
* @param app Die Hauptanwendung
* @param players Die Liste der Spieler mit ihren Figuren
*/
public TestWorld(MonopolyApp app) {
public TestWorld(MonopolyApp app, List<Player> players) {
this.app = app;
app.getGameLogic().addListener(this);
this.players = players;
}
/**
* Initialisiert die Szene und startet die Kamerabewegung.
* Initialisiert die Szene mit Spielfeld und Figuren.
*/
public void initializeScene() {
app.getGuiNode().detachAllChildren(); // Entferne GUI
app.getRootNode().detachAllChildren(); // Entferne andere Szenenobjekte
// Entferne bestehende Inhalte
app.getGuiNode().detachAllChildren();
app.getRootNode().detachAllChildren();
setSkyColor(); // Setze den Himmel auf hellblau
createBoard(); // Erstelle das Spielfeld
System.out.println("Szene initialisiert.");
// Erstelle den CameraController
cameraController = new CameraController(
app.getCamera(), // Die Kamera der App
Vector3f.ZERO, // Fokus auf die Mitte des Spielfelds
4, // Radius des Kreises
15, // Höhe der Kamera
0 // Geschwindigkeit der Bewegung
);
// Füge die Toolbar hinzu
toolbar = new Toolbar(app);
toolbar.open();
cameraController.setPosition(0);
}
/**
* Aktualisiert die Kameraposition.
*
* @param tpf Zeit pro Frame
*/
public void update(float tpf) {
if (cameraController != null) {
cameraController.update(tpf);
}
// Initialisiere Szene
setSkyColor();
createBoard();
createPlayerFigures(); // Lädt Figuren aus der bereits vorhandenen Liste
setupCamera();
}
/**
* Setzt die Hintergrundfarbe der Szene auf hellblau.
*/
private void setSkyColor() {
app.getViewPort().setBackgroundColor(new ColorRGBA(0.5f, 0.7f, 1.0f, 1.0f)); // Hellblauer Himmel
app.getViewPort().setBackgroundColor(new com.jme3.math.ColorRGBA(0.5f, 0.7f, 1.0f, 1.0f));
}
/**
* Erstelle das Spielfeld.
* Erstellt das Spielfeld und fügt es zur Szene hinzu.
*/
private void createBoard() {
// Erstelle ein Quadrat
Box box = new Box(10, 0.1f, 10); // Dünnes Quadrat für die Textur
Geometry geom = new Geometry("Board", box);
try {
// Erstelle das Spielfeld als flaches Rechteck
com.jme3.scene.shape.Box box = new com.jme3.scene.shape.Box(10, 0.1f, 10); // Breite, Höhe, Tiefe
com.jme3.scene.Geometry geom = new com.jme3.scene.Geometry("Board", box);
// Setze das Material mit Textur
Material mat = new Material(app.getAssetManager(), "Common/MatDefs/Misc/Unshaded.j3md");
Texture texture = app.getAssetManager().loadTexture("Pictures/board2.png");
mat.setTexture("ColorMap", texture);
geom.setMaterial(mat);
// Lade und setze das Material mit der Textur
com.jme3.material.Material mat = new com.jme3.material.Material(app.getAssetManager(), "Common/MatDefs/Misc/Unshaded.j3md");
com.jme3.texture.Texture texture = app.getAssetManager().loadTexture("Pictures/board2.png");
mat.setTexture("ColorMap", texture);
geom.setMaterial(mat);
app.getRootNode().attachChild(geom);
// Positioniere das Spielfeld in der Szene
geom.setLocalTranslation(0, -0.1f, 0); // Direkt auf der Grundebene
app.getRootNode().attachChild(geom);
System.out.println("Spielbrett erfolgreich erstellt und hinzugefügt.");
} catch (Exception e) {
System.err.println("Fehler beim Erstellen des Spielfelds: " + e.getMessage());
}
}
@Override
public void receivedEvent(EventCardEvent event) {
new EventCard(app, event.description()).open();
/**
* Erstellt die Spielfiguren basierend auf der bereits bekannten Spielerliste.
*/
private void createPlayerFigures() {
for (int i = 0; i < players.size(); i++) {
Player player = players.get(i);
try {
// Lade das 3D-Modell der Spielfigur
com.jme3.scene.Spatial model = app.getAssetManager().loadModel("Models/" + player.getFigure().getType() + ".j3O");
model.setLocalScale(0.5f); // Skaliere das Modell
model.setLocalTranslation(0, 0, -i * 2); // Positioniere die Figur auf dem Startfeld
app.getRootNode().attachChild(model);
System.out.println("Figur für Spieler " + player.getId() + " hinzugefügt.");
} catch (Exception e) {
System.err.println("Fehler beim Laden des Modells für Spieler " + player.getId() + ": " + e.getMessage());
}
}
}
/**
* Richtet die Kamera auf das Spielfeld aus.
*/
private void setupCamera() {
app.getCamera().setLocation(new com.jme3.math.Vector3f(0, 20, 20)); // Über dem Spielfeld
app.getCamera().lookAt(new com.jme3.math.Vector3f(0, 0, 0), com.jme3.math.Vector3f.UNIT_Y); // Fokus auf Spielfeldmitte
System.out.println("Kamera eingerichtet.");
}
/**
* Wird bei jedem Frame aufgerufen, um die Szene zu aktualisieren.
*
* @param tpf Zeit seit dem letzten Frame in Sekunden
*/
public void update(float tpf) {
if (cameraController != null) {
cameraController.update(tpf); // Aktualisiere die Kameraposition
}
}
@Override
@ -125,6 +141,7 @@ public class TestWorld implements GameEventListener{
new FoodFieldCard(app).open();
}
// }
}
}

View File

@ -155,10 +155,29 @@ public class Toolbar extends Dialog implements GameEventListener {
private void startDiceAnimation() {
animatingDice = true;
long startTime = System.currentTimeMillis();
new Thread(() -> {
Thread diceAnimation = new Thread(() -> {
int[] currentFace = {1};
try {
animateDice(startTime);
while (System.currentTimeMillis() - startTime < 2000) { // Animation läuft für 4 Sekunden
currentFace[0] = (currentFace[0] % 6) + 1;
String rotatingImage1 = diceToString(currentFace[0]);
String rotatingImage2 = diceToString((currentFace[0] % 6) + 1);
IconComponent newIcon1 = new IconComponent(rotatingImage1);
newIcon1.setIconSize(new Vector2f(100, 100));
app.enqueue(() -> imageLabel.setIcon(newIcon1));
IconComponent newIcon2 = new IconComponent(rotatingImage2);
newIcon2.setIconSize(new Vector2f(100, 100));
app.enqueue(() -> imageLabel2.setIcon(newIcon2));
// Warte 100 ms, bevor die Bilder wechseln
Thread.sleep(100);
}
// Animation beenden
animatingDice = false;
if (latestDiceRollEvent != null) {
showFinalDiceResult(latestDiceRollEvent);

View File

@ -0,0 +1,119 @@
package pp.monopoly.client.gui.popups;
import com.jme3.material.Material;
import com.jme3.material.RenderState.BlendMode;
import com.jme3.math.ColorRGBA;
import com.jme3.math.Vector3f;
import com.jme3.scene.Geometry;
import com.jme3.scene.shape.Quad;
import com.simsilica.lemur.Button;
import com.simsilica.lemur.Container;
import com.simsilica.lemur.Label;
import com.simsilica.lemur.component.QuadBackgroundComponent;
import com.simsilica.lemur.style.ElementId;
import pp.dialog.Dialog;
import pp.monopoly.client.MonopolyApp;
/**
* Bankrupt ist ein Overlay-Menü, welches aufgerufen werden kann, wenn man mit einem negativen Kontostand den Zug beenden möchte. // TODO welche menü-Klasse
*/
public class Bankrupt extends Dialog {
private final MonopolyApp app;
private final Geometry overlayBackground;
private final Container bankruptContainer;
private final Container backgroundContainer;
public Bankrupt(MonopolyApp app) {
super(app.getDialogManager());
this.app = app;
// Halbtransparentes Overlay hinzufügen
overlayBackground = createOverlayBackground();
app.getGuiNode().attachChild(overlayBackground);
// Create the background container
backgroundContainer = new Container();
backgroundContainer.setBackground(new QuadBackgroundComponent(new ColorRGBA(0.8657f, 0.8735f, 0.8892f, 1.0f))); // Darker background
app.getGuiNode().attachChild(backgroundContainer);
// Hauptcontainer für die Gebäudekarte
bankruptContainer = new Container();
bankruptContainer.setBackground(new QuadBackgroundComponent(new ColorRGBA(0.8657f, 0.8735f, 0.8892f, 1.0f)));
bankruptContainer.setPreferredSize(new Vector3f(550,250,10));
float padding = 10; // Padding around the settingsContainer for the background
backgroundContainer.setPreferredSize(bankruptContainer.getPreferredSize().addLocal(padding, padding, 0));
// Titel
// Die Namen werden dynamisch dem BoardManager entnommen
Label gateFieldTitle = bankruptContainer.addChild(new Label("Vorsicht !", new ElementId("settings-title"))); //TODO Dicke Schrift
gateFieldTitle.setFontSize(48);
gateFieldTitle.setColor(ColorRGBA.Black);
// Text, der auf der Karte steht
// Die Preise werden dynamisch dem BoardManager entnommen
Container Container = bankruptContainer.addChild(new Container());
Container.addChild(new Label("Du hast noch einen negativen Kontostand. Wenn du jetzt deinen Zug beendest, gehst du Bankrott und verlierst das Spiel!", new ElementId("label-Text")));
Container.setBackground(new QuadBackgroundComponent(new ColorRGBA(0.4657f, 0.4735f, 0.4892f, 1.0f)));
Container.setPreferredSize(bankruptContainer.getPreferredSize().addLocal(-250,-200,0));
// Beenden-Button
Button quitButton = bankruptContainer.addChild(new Button("Bestätigen", new ElementId("button")));
quitButton.setFontSize(32);
quitButton.addClickCommands(source -> close());
// Zentriere das Menü
bankruptContainer.setLocalTranslation(
(app.getCamera().getWidth() - bankruptContainer.getPreferredSize().x) / 2,
(app.getCamera().getHeight() + bankruptContainer.getPreferredSize().y) / 2,
8
);
backgroundContainer.setLocalTranslation(
(app.getCamera().getWidth() - bankruptContainer.getPreferredSize().x - padding) / 2,
(app.getCamera().getHeight() + bankruptContainer.getPreferredSize().y+ padding) / 2,
7
);
app.getGuiNode().attachChild(bankruptContainer);
}
/**
* Erstellt einen halbtransparenten Hintergrund für das Menü.
*
* @return Geometrie des Overlays
*/
private Geometry createOverlayBackground() {
Quad quad = new Quad(app.getCamera().getWidth(), app.getCamera().getHeight());
Geometry overlay = new Geometry("Overlay", quad);
Material material = new Material(app.getAssetManager(), "Common/MatDefs/Misc/Unshaded.j3md");
material.setColor("Color", new ColorRGBA(0, 0, 0, 0.5f)); // Halbtransparent
material.getAdditionalRenderState().setBlendMode(BlendMode.Alpha);
overlay.setMaterial(material);
overlay.setLocalTranslation(0, 0, 0);
return overlay;
}
/**
* Schließt das Menü und entfernt die GUI-Elemente.
*/
@Override
public void close() {
app.getGuiNode().detachChild(bankruptContainer); // Entferne das Menü
app.getGuiNode().detachChild(backgroundContainer); //Entfernt Rand
app.getGuiNode().detachChild(overlayBackground); // Entferne das Overlay
super.close();
}
@Override
public void escape() {
close();
}
}

View File

@ -69,7 +69,7 @@ public class ConfirmTrade extends Dialog {
// Kaufen-Button
Button negotiateButton = confirmTradeContainer.addChild(new Button("Verhandeln", new ElementId("button"))); //TODO ggf die Buttons Sprachabhängig von den Properties machen
negotiateButton.setFontSize(32);
negotiateButton.addClickCommands(s -> ifTopDialog( () -> {
negotiateButton.addClickCommands(s -> ifTopDialog( () -> { //TODO Buttonfunktion prüfen
app.getGameLogic().playSound(Sound.BUTTON);
}));
// Kaufen-Button

View File

@ -0,0 +1,122 @@
package pp.monopoly.client.gui.popups;
import com.jme3.material.Material;
import com.jme3.material.RenderState.BlendMode;
import com.jme3.math.ColorRGBA;
import com.jme3.math.Vector3f;
import com.jme3.scene.Geometry;
import com.jme3.scene.shape.Quad;
import com.simsilica.lemur.Button;
import com.simsilica.lemur.Container;
import com.simsilica.lemur.Label;
import com.simsilica.lemur.component.QuadBackgroundComponent;
import com.simsilica.lemur.style.ElementId;
import pp.dialog.Dialog;
import pp.monopoly.client.MonopolyApp;
import pp.monopoly.notification.Sound;
import static pp.monopoly.Resources.lookup;
/**
* TimeOut ist ein Overlay-Menü, welches aufgerufen wird, wenn die Verbindung zum Server unterbrochen wurde.
*/
public class TimeOut extends Dialog {
private final MonopolyApp app;
private final Geometry overlayBackground;
private final Container timeOutContainer;
private final Container backgroundContainer;
public TimeOut(MonopolyApp app) {
super(app.getDialogManager());
this.app = app;
// Halbtransparentes Overlay hinzufügen
overlayBackground = createOverlayBackground();
app.getGuiNode().attachChild(overlayBackground);
// Create the background container
backgroundContainer = new Container();
backgroundContainer.setBackground(new QuadBackgroundComponent(new ColorRGBA(0.8657f, 0.8735f, 0.8892f, 1.0f))); // Darker background
app.getGuiNode().attachChild(backgroundContainer);
// Hauptcontainer für die Gebäudekarte
timeOutContainer = new Container();
timeOutContainer.setBackground(new QuadBackgroundComponent(new ColorRGBA(0.8657f, 0.8735f, 0.8892f, 1.0f)));
timeOutContainer.setPreferredSize(new Vector3f(550,250,10));
float padding = 10; // Padding around the settingsContainer for the background
backgroundContainer.setPreferredSize(timeOutContainer.getPreferredSize().addLocal(padding, padding, 0));
// Titel
// Die Namen werden dynamisch dem BoardManager entnommen
Label gateFieldTitle = timeOutContainer.addChild(new Label("Vorsicht !", new ElementId("settings-title"))); //TODO dicke Schrift
gateFieldTitle.setFontSize(48);
gateFieldTitle.setColor(ColorRGBA.Black);
// Text, der auf der Karte steht
// Die Preise werden dynamisch dem BoardManager entnommen
Container propertyValuesContainer = timeOutContainer.addChild(new Container());
propertyValuesContainer.addChild(new Label("Du hast die Verbindung verloren und kannst nichts dagegen machen. Akzeptiere einfach, dass du verloren hast!", new ElementId("label-Text")));
propertyValuesContainer.setBackground(new QuadBackgroundComponent(new ColorRGBA(0.4657f, 0.4735f, 0.4892f, 1.0f)));
propertyValuesContainer.setPreferredSize(timeOutContainer.getPreferredSize().addLocal(-250,-200,0));
// Beenden-Button
Button quitButton = timeOutContainer.addChild(new Button("Bestätigen", new ElementId("button")));
quitButton.setFontSize(32);
quitButton.addClickCommands(source -> close());
// Zentriere das Menü
timeOutContainer.setLocalTranslation(
(app.getCamera().getWidth() - timeOutContainer.getPreferredSize().x) / 2,
(app.getCamera().getHeight() + timeOutContainer.getPreferredSize().y) / 2,
8
);
backgroundContainer.setLocalTranslation(
(app.getCamera().getWidth() - timeOutContainer.getPreferredSize().x - padding) / 2,
(app.getCamera().getHeight() + timeOutContainer.getPreferredSize().y+ padding) / 2,
7
);
app.getGuiNode().attachChild(timeOutContainer);
}
/**
* Erstellt einen halbtransparenten Hintergrund für das Menü.
*
* @return Geometrie des Overlays
*/
private Geometry createOverlayBackground() {
Quad quad = new Quad(app.getCamera().getWidth(), app.getCamera().getHeight());
Geometry overlay = new Geometry("Overlay", quad);
Material material = new Material(app.getAssetManager(), "Common/MatDefs/Misc/Unshaded.j3md");
material.setColor("Color", new ColorRGBA(0, 0, 0, 0.5f)); // Halbtransparent
material.getAdditionalRenderState().setBlendMode(BlendMode.Alpha);
overlay.setMaterial(material);
overlay.setLocalTranslation(0, 0, 0);
return overlay;
}
/**
* Schließt das Menü und entfernt die GUI-Elemente.
*/
@Override
public void close() {
app.getGuiNode().detachChild(timeOutContainer); // Entferne das Menü
app.getGuiNode().detachChild(backgroundContainer); //Entfernt Rand
app.getGuiNode().detachChild(overlayBackground); // Entferne das Overlay
super.close();
}
@Override
public void escape() {
close();
}
}

View File

@ -83,6 +83,10 @@ public class Player implements FieldVisitor<Void>{
public void setFigure(Figure figure) {
this.figure = figure;
}
public Figure getFigure(){
return figure;
}
public PlayerColor getColor() {
switch ((id%6)+1) {
@ -571,4 +575,8 @@ public class Player implements FieldVisitor<Void>{
}
}
@Override
public String toString() {
return "Player{name=" + name + ", figure=" + figure + "}";
}
}

View File

@ -1,14 +1,13 @@
package pp.monopoly.model;
import static java.lang.Math.max;
import static java.lang.Math.min;
import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
import com.jme3.network.serializing.Serializable;
import static java.lang.Math.max;
import static java.lang.Math.min;
@Serializable
public class Figure implements Item{
private final String type;
@ -313,5 +312,9 @@ public class Figure implements Item{
public void accept(VoidVisitor visitor) {
visitor.visit(this);
}
public String getType() {
return type;
}
}