diff --git a/Projekte/.run/MdgaApp.run.xml b/Projekte/.run/MdgaApp.run.xml deleted file mode 100644 index cfb2a51b..00000000 --- a/Projekte/.run/MdgaApp.run.xml +++ /dev/null @@ -1,19 +0,0 @@ - - - - diff --git a/Projekte/mdga/client/hs_err_pid54211.log b/Projekte/mdga/client/hs_err_pid54211.log new file mode 100644 index 00000000..9b6e3d33 --- /dev/null +++ b/Projekte/mdga/client/hs_err_pid54211.log @@ -0,0 +1,21 @@ +# +# A fatal error has been detected by the Java Runtime Environment: +# +# SIGSEGV (0xb) at pc=0x000070ba272e8104, pid=54211, tid=54346 +# +# JRE version: OpenJDK Runtime Environment Temurin-20.0.2+9 (20.0.2+9) (build 20.0.2+9) +# Java VM: OpenJDK 64-Bit Server VM Temurin-20.0.2+9 (20.0.2+9, mixed mode, sharing, tiered, compressed oops, compressed class ptrs, g1 gc, linux-amd64) +# Problematic frame: +# V [libjvm.so+0xee8104] SystemDictionary::find_or_define_helper(Symbol*, Handle, InstanceKlass*, JavaThread*)+0x304 +# +# Core dump will be written. Default location: Core dumps may be processed with "/usr/lib/systemd/systemd-coredump %P %u %g %s %t %c %h" (or dumping to /home/cedric/ProgProjekt/Gruppe-01/Projekte/mdga/client/core.54211) +# +# If you would like to submit a bug report, please visit: +# https://github.com/adoptium/adoptium-support/issues +# + +--------------- S U M M A R Y ------------ + +Command Line: -Ddebugger.agent.enable.coroutines=true -Djava.util.logging.config.file=logging.properties -Dkotlinx.coroutines.debug.enable.creation.stack.trace=false -Dkotlinx.coroutines.debug.enable.flows.stack.trace=true -Dkotlinx.coroutines.debug.enable.mutable.state.flows.stack.trace=true -agentlib:jdwp=transport=dt_socket,server=n,suspend=y,address=127.0.0.1:40559 -javaagent:/usr/share/idea/plugins/java/lib/rt/debugger-agent.jar -Dfile.encoding=UTF-8 -Duser.country=US -Duser.language=en -Duser.variant -ea pp.mdga.client.MdgaApp + +Host: AMD Ryzen 5 8640HS w/ Radeon 760M Graphics, 12 cores, 14G, \ No newline at end of file diff --git a/Projekte/mdga/client/hs_err_pid60653.log b/Projekte/mdga/client/hs_err_pid60653.log new file mode 100644 index 00000000..974a6ce1 --- /dev/null +++ b/Projekte/mdga/client/hs_err_pid60653.log @@ -0,0 +1,171 @@ +# +# A fatal error has been detected by the Java Runtime Environment: +# +# SIGSEGV (0xb) at pc=0x00007fc14e0eef41, pid=60653, tid=60689 +# +# JRE version: OpenJDK Runtime Environment (21.0.5+11) (build 21.0.5+11) +# Java VM: OpenJDK 64-Bit Server VM (21.0.5+11, mixed mode, sharing, tiered, compressed oops, compressed class ptrs, g1 gc, linux-amd64) +# Problematic frame: +# C [libgallium-24.2.8-arch1.1.so+0x8eef41] +# +# Core dump will be written. Default location: Core dumps may be processed with "/usr/lib/systemd/systemd-coredump %P %u %g %s %t %c %h" (or dumping to /home/cedric/ProgProjekt/Gruppe-01/Projekte/mdga/client/core.60653) +# +# If you would like to submit a bug report, please visit: +# https://bugreport.java.com/bugreport/crash.jsp +# The crash happened outside the Java Virtual Machine in native code. +# See problematic frame for where to report the bug. +# + +--------------- S U M M A R Y ------------ + +Command Line: -Ddebugger.agent.enable.coroutines=true -Djava.util.logging.config.file=logging.properties -Dkotlinx.coroutines.debug.enable.creation.stack.trace=false -Dkotlinx.coroutines.debug.enable.flows.stack.trace=true -Dkotlinx.coroutines.debug.enable.mutable.state.flows.stack.trace=true -agentlib:jdwp=transport=dt_socket,server=n,suspend=y,address=127.0.0.1:39131 -javaagent:/usr/share/idea/plugins/java/lib/rt/debugger-agent.jar -Dfile.encoding=UTF-8 -Duser.country=US -Duser.language=en -Duser.variant -ea pp.mdga.client.MdgaApp + +Host: AMD Ryzen 5 8640HS w/ Radeon 760M Graphics, 12 cores, 14G, Manjaro Linux +Time: Sun Dec 8 18:11:23 2024 CET elapsed time: 295.650309 seconds (0d 0h 4m 55s) + +--------------- T H R E A D --------------- + +Current thread (0x00007fc17ca803b0): JavaThread "jME3 Main" [_thread_in_native, id=60689, stack(0x00007fc159425000,0x00007fc159525000) (1024K)] + +Stack: [0x00007fc159425000,0x00007fc159525000], sp=0x00007fc159522300, free space=1012k +Native frames: (J=compiled Java code, j=interpreted, Vv=VM code, C=native code) +C [libgallium-24.2.8-arch1.1.so+0x8eef41] +C [libgallium-24.2.8-arch1.1.so+0xf4a849] +C [libgallium-24.2.8-arch1.1.so+0x6ccb71] +C [libgallium-24.2.8-arch1.1.so+0x6c58ae] +C [libgallium-24.2.8-arch1.1.so+0x6c6013] +C [libgallium-24.2.8-arch1.1.so+0x6cddf8] +C [libgallium-24.2.8-arch1.1.so+0x141327] +C [libgallium-24.2.8-arch1.1.so+0x5fc8b] +C [libGLX_mesa.so.0+0x4f2e0] +C [libGLX_mesa.so.0+0x40496] +C [libGLX_mesa.so.0+0x2efa5] +J 2042 org.lwjgl.system.JNI.invokePV(JJ)V (0 bytes) @ 0x00007fc16c1abb6f [0x00007fc16c1abaa0+0x00000000000000cf] +J 4039 c1 org.lwjgl.glfw.GLFW.glfwSwapBuffers(J)V (21 bytes) @ 0x00007fc164d8684c [0x00007fc164d86760+0x00000000000000ec] +J 3912 c1 com.jme3.system.lwjgl.LwjglWindow.runLoop()V (177 bytes) @ 0x00007fc164d44b34 [0x00007fc164d442c0+0x0000000000000874] +j com.jme3.system.lwjgl.LwjglWindow.run()V+54 +j java.lang.Thread.runWith(Ljava/lang/Object;Ljava/lang/Runnable;)V+5 java.base@21.0.5 +j java.lang.Thread.run()V+19 java.base@21.0.5 +v ~StubRoutines::call_stub 0x00007fc16bb37cc6 +V [libjvm.so+0x6d0894] +V [libjvm.so+0x6d14fd] +V [libjvm.so+0x79a7be] +V [libjvm.so+0x6cac55] +V [libjvm.so+0x9d62c1] +C [libc.so.6+0x9439d] +Java frames: (J=compiled Java code, j=interpreted, Vv=VM code) +J 2042 org.lwjgl.system.JNI.invokePV(JJ)V (0 bytes) @ 0x00007fc16c1abafc [0x00007fc16c1abaa0+0x000000000000005c] +J 4039 c1 org.lwjgl.glfw.GLFW.glfwSwapBuffers(J)V (21 bytes) @ 0x00007fc164d8684c [0x00007fc164d86760+0x00000000000000ec] +J 3912 c1 com.jme3.system.lwjgl.LwjglWindow.runLoop()V (177 bytes) @ 0x00007fc164d44b34 [0x00007fc164d442c0+0x0000000000000874] +j com.jme3.system.lwjgl.LwjglWindow.run()V+54 +j java.lang.Thread.runWith(Ljava/lang/Object;Ljava/lang/Runnable;)V+5 java.base@21.0.5 +j java.lang.Thread.run()V+19 java.base@21.0.5 +v ~StubRoutines::call_stub 0x00007fc16bb37cc6 + +siginfo: si_signo: 11 (SIGSEGV), si_code: 1 (SEGV_MAPERR), si_addr: 0x00000000000000c9 + +Registers: +RAX=0x0000000000000000, RBX=0x00007fc09825b2a0, RCX=0x0000000000000006, RDX=0x0000000028200000 +RSP=0x00007fc159522300, RBP=0x00007fc159522310, RSI=0x00007fc0998d3604, RDI=0x00007fc09825b7a0 +R8 =0x0000000000000006, R9 =0x00000000aa959a6a, R10=0x0000000000000263, R11=0x00007fc099bc36c0 +R12=0x00007fc0998d35e0, R13=0x000000058bc5f100, R14=0x000000058bc5f140, R15=0x0000000000000040 +RIP=0x00007fc14e0eef41, EFLAGS=0x0000000000010202, CSGSFS=0x002b000000000033, ERR=0x0000000000000004 + TRAPNO=0x000000000000000e + + +Register to memory mapping: + +RAX=0x0 is null +RBX=0x00007fc09825b2a0 points into unknown readable memory: 0x00007fc098239c40 | 40 9c 23 98 c0 7f 00 00 +RCX=0x0000000000000006 is an unknown value +RDX=0x0000000028200000 is an unknown value +RSP=0x00007fc159522300 is pointing into the stack for thread: 0x00007fc17ca803b0 +RBP=0x00007fc159522310 is pointing into the stack for thread: 0x00007fc17ca803b0 +RSI=0x00007fc0998d3604 points into unknown readable memory: 00 00 00 00 +RDI=0x00007fc09825b7a0 points into unknown readable memory: 0x00001c7c00000265 | 65 02 00 00 7c 1c 00 00 +R8 =0x0000000000000006 is an unknown value +R9 =0x00000000aa959a6a is an unknown value +R10=0x0000000000000263 is an unknown value +R11=0x00007fc099bc36c0 points into unknown readable memory: 0x00007fc14e121570 | 70 15 12 4e c1 7f 00 00 +R12=0x00007fc0998d35e0 points into unknown readable memory: 0x0000000000000000 | 00 00 00 00 00 00 00 00 +R13=0x000000058bc5f100 is an unknown value +R14=0x000000058bc5f140 is an unknown value +R15=0x0000000000000040 is an unknown value + +Top of Stack: (sp=0x00007fc159522300) +0x00007fc159522300: 00007fc09825b2a0 ffffffffffffffff +0x00007fc159522310: 00007fc1595223d0 00007fc14e74a849 +0x00007fc159522320: 0000000000000000 00000000cc0016c8 +0x00007fc159522330: 00007fc09920b000 00007fc100000004 +0x00007fc159522340: 00007fc100000001 00007fc100000000 +0x00007fc159522350: ffff800100000002 00007fc09825b7a0 +0x00007fc159522360: 00007fc1595223e0 0000000100000b02 +0x00007fc159522370: 0000000000000000 00007fc0983eca88 +0x00007fc159522380: 00007fc100000000 00007fc099e33780 +0x00007fc159522390: 00007fc159523170 b36c5690f9bb0900 +0x00007fc1595223a0: 00007fc15951fd20 00007fc0983eca80 +0x00007fc1595223b0: 00007fc09825b2a0 00007fc0983edb60 +0x00007fc1595223c0: 00007fc098415b10 00007fc0983ec850 +0x00007fc1595223d0: 00007fc159523280 00007fc14deccb71 +0x00007fc1595223e0: 00000bdc00000000 00007fc100000000 +0x00007fc1595223f0: 00007fc159523290 00007fc159523294 +0x00007fc159522400: 00007fc159523320 00007fc159523324 +0x00007fc159522410: 00007fc1595231b0 00007fc1595231b4 +0x00007fc159522420: 00007fc159522860 00007fc164c8401c +0x00007fc159522430: 00007fc159523310 00007fc159523314 +0x00007fc159522440: 00007fc1595232a0 00007fc1595232a4 +0x00007fc159522450: 00007fc159522860 00007fc159523334 +0x00007fc159522460: 00007fc159523400 00007fc159523404 +0x00007fc159522470: 00007fc1595232d0 00007fc1595232d4 +0x00007fc159522480: 00007fc16bc61f10 00007fc0c80123d0 +0x00007fc159522490: 00007fc1595231f0 00007fc1595231f4 +0x00007fc1595224a0: 00007fc1595223e0 00000000e31c914f +0x00007fc1595224b0: 00007fc159523350 00007fc159523354 +0x00007fc1595224c0: 00007fc1595232e0 00007fc1595232e4 +0x00007fc1595224d0: 00007f0000000000 00000000e3193478 +0x00007fc1595224e0: 00007fc159523440 00007fc159523444 +0x00007fc1595224f0: 00007fc159523310 00007fc159523314 + +Instructions: (pc=0x00007fc14e0eef41) +0x00007fc14e0eee41: 0f 1e fa 55 48 83 c6 24 48 89 e5 41 55 41 54 53 +0x00007fc14e0eee51: 48 89 fb 48 83 ec 08 8b 97 00 05 00 00 44 0f b7 +0x00007fc14e0eee61: 6e f0 48 8b 87 08 05 00 00 49 89 d4 45 01 ec 48 +0x00007fc14e0eee71: 8d 3c 90 42 8d 14 ad 00 00 00 00 ff 15 ee 7e c3 +0x00007fc14e0eee81: 01 44 89 a3 00 05 00 00 48 83 c4 08 5b 41 5c 41 +0x00007fc14e0eee91: 5d 5d c3 66 2e 0f 1f 84 00 00 00 00 00 66 90 f3 +0x00007fc14e0eeea1: 0f 1e fa 55 48 89 e5 41 57 41 56 41 55 41 54 41 +0x00007fc14e0eeeb1: 89 f4 53 48 89 fb 48 83 ec 08 4e 8b b4 e7 88 09 +0x00007fc14e0eeec1: 00 00 8b 97 00 05 00 00 48 8b 87 08 05 00 00 45 +0x00007fc14e0eeed1: 0f b7 7e 14 49 89 d5 49 8d 76 24 48 8d 3c 90 45 +0x00007fc14e0eeee1: 01 fd 42 8d 14 bd 00 00 00 00 ff 15 7f 7e c3 01 +0x00007fc14e0eeef1: 44 89 ab 00 05 00 00 4e 89 b4 e3 d8 09 00 00 48 +0x00007fc14e0eef01: 83 c4 08 5b 41 5c 41 5d 41 5e 41 5f 5d c3 90 f3 +0x00007fc14e0eef11: 0f 1e fa 55 89 f0 48 89 e5 41 54 53 4c 8b a4 c7 +0x00007fc14e0eef21: 88 09 00 00 48 89 fb e8 73 ff ff ff 49 8b 84 24 +0x00007fc14e0eef31: 80 01 00 00 ba 00 00 20 28 48 8d bb 00 05 00 00 +0x00007fc14e0eef41: 0f b6 88 c9 00 00 00 48 8b b0 b0 00 00 00 48 8b +0x00007fc14e0eef51: 83 f0 04 00 00 ff 90 00 01 00 00 49 8b 04 24 48 +0x00007fc14e0eef61: 85 c0 74 13 48 89 df be ff ff ff ff 5b 41 5c 5d +0x00007fc14e0eef71: ff e0 0f 1f 44 00 00 5b 41 5c 5d c3 0f 1f 00 f3 +0x00007fc14e0eef81: 0f 1e fa 66 0f ef c0 31 c9 ba 01 00 00 00 0f 11 +0x00007fc14e0eef91: 87 d8 09 00 00 0f 11 87 e8 09 00 00 0f 11 87 f8 +0x00007fc14e0eefa1: 09 00 00 0f 11 87 08 0a 00 00 0f 11 87 18 0a 00 +0x00007fc14e0eefb1: 00 66 66 2e 0f 1f 84 00 00 00 00 00 0f 1f 00 48 +0x00007fc14e0eefc1: 83 bc cf 88 09 00 00 00 74 0d 48 89 d0 48 d3 e0 +0x00007fc14e0eefd1: 48 09 87 80 09 00 00 48 83 c1 01 48 83 f9 0a 75 +0x00007fc14e0eefe1: de c3 66 2e 0f 1f 84 00 00 00 00 00 0f 1f 00 f3 +0x00007fc14e0eeff1: 0f 1e fa 55 48 89 e5 41 56 41 89 d6 41 55 41 89 +0x00007fc14e0ef001: f5 8d 34 b5 28 00 00 00 41 54 49 89 fc bf 01 00 +0x00007fc14e0ef011: 00 00 53 ff 15 7e 89 c3 01 48 89 c3 48 85 c0 74 +0x00007fc14e0ef021: 2a 66 44 89 68 1a 41 0f b6 ce 48 8d 78 08 41 0f +0x00007fc14e0ef031: b6 94 24 97 08 00 00 49 8d b4 24 90 02 00 00 c0 + + +Stack slot to memory mapping: + +stack at sp + 0 slots: 0x00007fc09825b2a0 points into unknown readable memory: 0x00007fc098239c40 | 40 9c 23 98 c0 7f 00 00 +stack at sp + 1 slots: 0xffffffffffffffff is an unknown value +stack at sp + 2 slots: 0x00007fc1595223d0 is pointing into the stack for thread: 0x00007fc17ca803b0 +stack at sp + 3 slots: 0x00007fc14e74a849: in /usr/lib/libgallium-24.2.8-arch1.1.so at 0x00007fc14d800000 +stack at sp + 4 slots: 0x0 is null +stack at sp + 5 slots: \ No newline at end of file diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/NotificationSynchronizer.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/NotificationSynchronizer.java index 87e535c4..4cb2ca07 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/NotificationSynchronizer.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/NotificationSynchronizer.java @@ -121,6 +121,7 @@ private void handleGame(Notification notification) { delay = STANDARD_DELAY; } else if (notification instanceof ActivePlayerNotification n) { gameView.getGuiHandler().setActivePlayer(n.getColor()); + boardHandler.hideDice(); if(n.getColor() != ownColor) boardHandler.showDice(n.getColor()); app.getAcousticHandler().playSound(MdgaSound.UI90); delay = STANDARD_DELAY; @@ -159,17 +160,19 @@ private void handleGame(Notification notification) { } else if (notification instanceof HomeMoveNotification home) { boardHandler.movePieceHomeAnim(home.getPieceId(), home.getHomeIndex()); guiHandler.hideText(); - app.getGameLogic().selectAnimationEnd(); + waitForAnimation = true; } else if (notification instanceof InterruptNotification notification1) { gameView.enterInterrupt(notification1.getColor()); } else if (notification instanceof MovePieceNotification n) { if(n.isMoveStart()) { //StartMove boardHandler.movePieceStartAnim(n.getPiece(), n.getMoveIndex()); + waitForAnimation = true; } else { //InfieldMove boardHandler.movePieceAnim(n.getPiece(), n.getStartIndex(), n.getMoveIndex()); + waitForAnimation = true; } guiHandler.hideText(); } else if (notification instanceof ThrowPieceNotification n) { @@ -207,7 +210,6 @@ public void run() { waitForAnimation = true; } else { - boardHandler.hideDice(); if (n.isTurbo()) guiHandler.showRolledDiceMult(n.getEyes(), n.getMultiplier(), n.getColor()); else guiHandler.showRolledDice(n.getEyes(), n.getColor()); } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/board/BoardHandler.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/board/BoardHandler.java index 04d0e5bb..aaf07489 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/board/BoardHandler.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/board/BoardHandler.java @@ -442,6 +442,7 @@ private void moveHomePiece(UUID uuid, int index){ pieceControl.setRotation(getRotationMove(firstHomeNode.getLocation(), lastHomeNode.getLocation())); app.getModelSynchronize().animationEnd(); + app.getModelSynchronize().animationEnd(); } /** @@ -473,6 +474,7 @@ private void movePieceStart(UUID uuid, int nodeIndex){ removeItemFromMapList(waitingPiecesMap, color, pieceControl); waitingNodes.get(color).remove(uuid); app.getModelSynchronize().animationEnd(); + app.getModelSynchronize().animationEnd(); } /** @@ -486,6 +488,7 @@ private void movePiece(UUID uuid, int curIndex, int moveIndex){ movePieceRek(uuid, curIndex, moveIndex); app.getModelSynchronize().animationEnd(); + app.getModelSynchronize().animationEnd(); } /** @@ -538,7 +541,6 @@ public void shieldPiece(UUID uuid){ * @param uuid the UUID of the piece to unshield */ public void unshieldPiece(UUID uuid){ - pieces.get(uuid).deactivateShield(); } @@ -719,6 +721,8 @@ public void clearSelectable(){ p.unHighlight(); p.setSelectable(false); p.setHoverable(false); + if(selectedPieceNodeMap.get(p) != null) selectedPieceNodeMap.get(p).unSelect(); + if(selectedPieceNodeMap.get(p) != null) selectedPieceNodeMap.get(p).unHighlight(); } for(PieceControl p : selectableOwnPieces) { p.unSelect(); diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/board/PieceControl.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/board/PieceControl.java index 8db0b9b1..d317342f 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/board/PieceControl.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/board/PieceControl.java @@ -150,6 +150,9 @@ public void rotateInit() { * This adds a visual shield effect in the form of a rotating ring. */ public void activateShield(){ + if(shieldRing != null){ + deactivateShield(); + } shieldRing = assetManager.loadModel(Asset.shieldRing.getModelPath()); shieldRing.scale(1f); shieldRing.rotate((float) Math.toRadians(0), 0, (float) Math.toRadians(0)); diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/CardLayerHandler.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/CardLayerHandler.java index 88b2351d..eda19ab4 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/CardLayerHandler.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/CardLayerHandler.java @@ -29,6 +29,7 @@ public class CardLayerHandler { private DiceControl diceControl; private final Map bonusCardControlMap = new HashMap<>(); + private final List cardOrder = new ArrayList<>(); private final Map bonusCardIntegerMap = new HashMap<>(); private final Set selectableCards = new HashSet<>(); @@ -80,14 +81,13 @@ public void addCard(BonusCard card) { if (card == BonusCard.HIDDEN) throw new RuntimeException("Can't add hidden card to GUI"); if (!bonusCardControlMap.containsKey(card)) { - CardControl control = createCard(bonusToAsset(card), nextPos()); - bonusCardControlMap.put(card, control); - cardLayer.addSpatial(control.getRoot()); + cardOrder.add(card); } int newNum = bonusCardIntegerMap.getOrDefault(card, 0) + 1; bonusCardIntegerMap.put(card, newNum); - bonusCardControlMap.get(card).setNumCard(newNum); + + updateCard(); } public void removeCard(BonusCard card){ @@ -95,12 +95,11 @@ public void removeCard(BonusCard card){ bonusCardIntegerMap.put(card, bonusCardIntegerMap.get(card) - 1); if(bonusCardIntegerMap.get(card) <= 0){ - cardLayer.deleteSpatial(bonusCardControlMap.get(card).getRoot()); bonusCardIntegerMap.remove(card); - bonusCardControlMap.remove(card); + cardOrder.remove(card); } - - } + updateCard(); + } else throw new RuntimeException("card is not in bonusCardControlMap"); } public void clearSelectableCards() { @@ -114,6 +113,22 @@ public void clearSelectableCards() { cardSelect = null; } + private void updateCard(){ + for(BonusCard card : bonusCardControlMap.keySet()){ + CardControl control = bonusCardControlMap.get(card); + cardLayer.deleteSpatial(control.getRoot()); + } + bonusCardControlMap.clear(); + + for(int i = 0; i < cardOrder.size(); i++){ + BonusCard card = cardOrder.get(i); + CardControl control = createCard(bonusToAsset(card), nextPos(i)); + control.setNumCard(bonusCardIntegerMap.get(card)); + cardLayer.addSpatial(control.getRoot()); + bonusCardControlMap.put(card, control); + } + } + public void setSelectableCards(List select) { for (BonusCard card : select) { selectableCards.add(bonusCardControlMap.get(card)); @@ -171,8 +186,8 @@ private Asset bonusToAsset(BonusCard card) { }; } - private Vector3f nextPos() { - return START.add(MARGIN.mult(bonusCardControlMap.size())); + private Vector3f nextPos(int i) { + return START.add(MARGIN.mult(i)); } private Camera createOverlayCam() { diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/DiceControl.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/DiceControl.java index 42e356aa..e90f20f5 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/DiceControl.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/DiceControl.java @@ -21,7 +21,7 @@ public class DiceControl extends AbstractControl { private Quaternion targetRotation; private final Vector3f angularVelocity = new Vector3f(); - private float deceleration = 0.5f; + private float deceleration = 1f; private float timeElapsed = 0.0f; private float rollDuration = 1f; private static final int ANGULAR_MIN = 5; diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/PlayerNameHandler.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/PlayerNameHandler.java index 014c00a9..083319e6 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/PlayerNameHandler.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/gui/PlayerNameHandler.java @@ -128,7 +128,7 @@ private BitmapText createName(String name, boolean first, boolean own){ //renderedSize = 45 hudText.setSize(TEXT_SIZE); hudText.setColor(first ? ACTIVE_COLOR : own ? OWN_COLOR : NORMAL_COLOR); - hudText.setText(name); + hudText.setText(own ? name + " (Du)" : name); hudText.setLocalTranslation(PADDING_LEFT,hudText.getHeight()/2, 0); return hudText; } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/server/MdgaServer.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/server/MdgaServer.java index 14b5436e..0545fca7 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/server/MdgaServer.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/server/MdgaServer.java @@ -139,6 +139,7 @@ private void initializeSerializables() { Serializer.registerClass(UpdateTSKMessage.class); Serializer.registerClass(WaitPieceMessage.class); Serializer.registerClass(IncorrectRequestMessage.class); + Serializer.registerClass(SpectatorMessage.class); Serializer.registerClass(Player.class); Serializer.registerClass(Statistic.class); Serializer.registerClass(Board.class); diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/view/GameView.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/view/GameView.java index bd77237a..f2a51ee2 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/view/GameView.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/view/GameView.java @@ -18,7 +18,7 @@ public class GameView extends MdgaView { private GuiHandler guiHandler; private ButtonLeft leaveButton; - private ButtonRight confirmButton; + public ButtonRight confirmButton; private ButtonRight noPowerButton; @@ -28,6 +28,9 @@ public class GameView extends MdgaView { private FilterPostProcessor fpp; + public boolean needConfirm = false; + public boolean needNoPower = false; + private Node guiHandlerNode = new Node(); public GameView(MdgaApp app) { @@ -116,19 +119,26 @@ public Color getOwnColor() { public void needConfirm() { noPowerButton.hide(); confirmButton.show(); + + needConfirm = true; } public void noConfirm() { confirmButton.hide(); + + needConfirm = false; } public void showNoPower() { confirmButton.hide(); noPowerButton.show(); + + needNoPower = true; } public void hideNoPower() { noPowerButton.hide(); + needNoPower = false; } public void enterInterrupt(Color color) { diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/view/MdgaView.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/view/MdgaView.java index a16cc2d7..a3da3d87 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/view/MdgaView.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/view/MdgaView.java @@ -59,7 +59,6 @@ public void enter() { public void leave() { onLeave(); - settingsButton.hide(); while (settingsDepth > 0) { @@ -197,7 +196,13 @@ public void pressForward() { } if (this instanceof GameView gameView) { - app.getAcousticHandler().playSound(MdgaSound.WRONG_INPUT); + if(gameView.needConfirm) { + app.getModelSynchronize().confirm(); + } else if(gameView.needNoPower) { + app.getModelSynchronize().confirm(); + } else { + app.getAcousticHandler().playSound(MdgaSound.WRONG_INPUT); + } } if (this instanceof CeremonyView ceremonyView) { diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/GameState.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/GameState.java index bb1d4333..32e23fd7 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/GameState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/GameState.java @@ -294,17 +294,14 @@ public void received(ChoosePieceStateMessage msg){ @Override public void received(DrawCardMessage msg){ - if(msg.getCard() instanceof HiddenCard){ + logic.getGame().getActivePlayer().addHandCard(msg.getCard()); + if (msg.getCard() instanceof HiddenCard) { logic.addNotification(new DrawCardNotification(logic.getGame().getActiveColor(), BonusCard.HIDDEN)); - } else if(msg.getCard() instanceof TurboCard) { - logic.addNotification(new AcquireCardNotification(BonusCard.TURBO)); - } else if(msg.getCard() instanceof ShieldCard) { - logic.addNotification(new AcquireCardNotification(BonusCard.SHIELD)); - } else if(msg.getCard() instanceof SwapCard) { - logic.addNotification(new AcquireCardNotification(BonusCard.SWAP)); - } else { - throw new RuntimeException(); } + else{ + logic.addNotification(new AcquireCardNotification(msg.getCard().getCard())); + } + } /** diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/GameStates.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/GameStates.java index ccc1734b..e8d5555c 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/GameStates.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/GameStates.java @@ -37,18 +37,13 @@ protected void handlePowerCard(PlayCardMessage msg) { logic.getGame().getDiscardPile().add(msg.getCard()); } - protected void throwPiece(Piece piece) { - logic.getGame().getBoard().getInfield()[logic.getGame().getBoard().getInfieldIndexOfPiece(piece)].clearOccupant(); - logic.getGame().getPlayerByColor(piece.getColor()).addWaitingPiece(piece); - logic.addNotification(new ThrowPieceNotification(piece.getUuid(), piece.getColor())); - logic.getGame().getPlayerByColor(piece.getColor()).getPlayerStatistic().increasePiecesBeingThrown(); - logic.getGame().getGameStatistics().increasePiecesBeingThrown(); - piece.setState(PieceState.WAITING); - } - private void handleShield(UUID uuid) { - if (logic.getGame().getBoard().getInfieldIndexOfPiece(logic.getGame().getPieceThroughUUID(uuid)) % 10 != 0) { + Board board = logic.getGame().getBoard(); + Piece piece = logic.getGame().getPieceThroughUUID(uuid); + Node node = board.getInfield()[board.getInfieldIndexOfPiece(piece)]; + if (node.isStart()) { logic.getGame().getPieceThroughUUID(uuid).setShield(ShieldState.SUPPRESSED); + logic.addNotification(new ShieldActiveNotification(uuid)); logic.addNotification(new ShieldSuppressedNotification(uuid)); } else { logic.getGame().getPieceThroughUUID(uuid).setShield(ShieldState.ACTIVE); @@ -66,6 +61,22 @@ private void swapPieces(Piece messageOwn, Piece messageEnemy) { ownNode.setOccupant(modelEnemy); enemyNode.setOccupant(modelOwn); + logic.addNotification(new SwapPieceNotification(modelOwn.getUuid(), modelEnemy.getUuid())); + checkShieldAfterSwap(enemyNode, modelOwn); + checkShieldAfterSwap(ownNode, modelEnemy); + + } + + private void checkShieldAfterSwap(Node node, Piece piece){ + if (node.isStart()){ + if (piece.isShielded()){ + piece.setShield(ShieldState.SUPPRESSED); + logic.addNotification(new ShieldSuppressedNotification(piece.getUuid())); + } + } else if (piece.isSuppressed()){ + piece.setShield(ShieldState.ACTIVE); + logic.addNotification(new ShieldActiveNotification(piece.getUuid())); + } } } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/SpectatorState.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/SpectatorState.java index d0ae32c9..e6da6261 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/SpectatorState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/SpectatorState.java @@ -3,8 +3,10 @@ import pp.mdga.client.ClientGameLogic; import pp.mdga.client.ClientState; import pp.mdga.client.GameState; +import pp.mdga.game.BonusCard; import pp.mdga.game.Piece; import pp.mdga.game.PieceState; +import pp.mdga.game.card.HiddenCard; import pp.mdga.message.server.*; import pp.mdga.notification.*; @@ -33,7 +35,12 @@ public void received(CeremonyMessage msg) { @Override public void received(DrawCardMessage msg){ - logic.addNotification(new DrawCardNotification(logic.getGame().getActiveColor(), msg.getCard().getCard())); + logic.getGame().getActivePlayer().addHandCard(msg.getCard()); + if (msg.getCard() instanceof HiddenCard) { + logic.addNotification(new DrawCardNotification(logic.getGame().getActiveColor(), BonusCard.HIDDEN)); + } + + //stats logic.getGame().getPlayerByColor(logic.getGame().getActiveColor()).getPlayerStatistic().increaseActivatedBonusNodes(); logic.getGame().getGameStatistics().increaseActivatedBonusNodes(); } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/TurnState.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/TurnState.java index 97d0238f..ec119d18 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/TurnState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/TurnState.java @@ -40,6 +40,7 @@ public TurnState(ClientState parent, ClientGameLogic logic) { @Override public void enter() { + logic = logic; for (Piece piece : logic.getGame().getPlayerByColor(logic.getGame().getActiveColor()).getPieces()) { if (piece.isShielded() || piece.isSuppressed()){ piece.setShield(ShieldState.NONE); @@ -159,11 +160,6 @@ public void received(ChoosePieceStateMessage msg){ state.received(msg); } - @Override - public void received(DrawCardMessage msg){ - - } - public ChoosePieceState getChoosePiece() { return choosePieceState; } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/WaitingState.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/WaitingState.java index 82a7d1dc..30cf5c84 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/WaitingState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/WaitingState.java @@ -3,8 +3,10 @@ import pp.mdga.client.ClientGameLogic; import pp.mdga.client.ClientState; import pp.mdga.client.GameState; +import pp.mdga.game.Node; import pp.mdga.game.Piece; import pp.mdga.game.PieceState; +import pp.mdga.game.ShieldState; import pp.mdga.message.server.*; import pp.mdga.notification.*; @@ -33,12 +35,6 @@ public void received(CeremonyMessage msg) { logic.setState(logic.getCeremony()); } - @Override - public void received(DiceNowMessage msg) { - logic.addNotification(new DiceNowNotification()); - parent.setState(parent.getTurn()); - } - @Override public void received(DieMessage msg) { logic.getGame().setDiceEyes(msg.getDiceEye()); @@ -48,8 +44,6 @@ public void received(DieMessage msg) { else { logic.addNotification(new RollDiceNotification(logic.getGame().getActiveColor(), msg.getDiceEye())); } -// logic.addNotification(new RollDiceNotification(logic.getGame().getActiveColor(), logic.getGame().getDiceEyes())); - //stats if (msg.getDiceEye() == 6) { @@ -73,24 +67,61 @@ public void received(ActivePlayerMessage msg) { logic.getGame().setActiveColor(msg.getColor()); if(msg.getColor() == logic.getGame().getPlayers().get(logic.getOwnPlayerId()).getColor()) { parent.setState(parent.getTurn()); + } else { + for (Piece piece : logic.getGame().getActivePlayer().getPieces()){ + if (piece.isShielded() || piece.isSuppressed()){ + logic.addNotification(new RemoveShieldNotification(piece.getUuid())); + piece.setShield(ShieldState.NONE); + } + } } } -// @Override -// public void received(DrawCardMessage msg){ -// logic.addNotification(new DrawCardNotification(logic.getGame().getActiveColor(), msg.getCard().getCard())); -// logic.getGame().getPlayerByColor(logic.getGame().getActiveColor()).getPlayerStatistic().increaseActivatedBonusNodes(); -// logic.getGame().getGameStatistics().increaseActivatedBonusNodes(); -// } - @Override public void received(MoveMessage msg) { Piece piece = logic.getGame().getPieceThroughUUID(msg.getPiece().getUuid()); if (msg.isHomeMove()) { - logic.addNotification(new HomeMoveNotification(piece.getUuid(), msg.getTargetIndex())); - logic.getGame().getBoard().getInfield()[logic.getGame().getBoard().getInfieldIndexOfPiece(piece)].clearOccupant(); - logic.getGame().getPlayerByColor(piece.getColor()).setPieceInHome(msg.getTargetIndex(), piece); - } else { + if(piece.getState().equals(PieceState.HOME)){ + logic.addNotification(new HomeMoveNotification(piece.getUuid(), msg.getTargetIndex())); + int pieceHomeIndex = logic.getGame().getActivePlayer().getHomeIndexOfPiece(piece); + Node pieceNode = logic.getGame().getActivePlayer().getHomeNodes()[pieceHomeIndex]; + + //gets the oldNode + int homeIndex = logic.getGame().getActivePlayer().getHomeIndexOfPiece(piece); + Node oldNode = logic.getGame().getActivePlayer().getHomeNodes()[homeIndex]; + //gets the targetNode + Node targetNode = logic.getGame().getActivePlayer().getHomeNodes()[msg.getTargetIndex()]; + if (msg.getTargetIndex() ==logic.getGame().getActivePlayer().getHighestHomeIdx()) { + piece.setState(PieceState.HOMEFINISHED); + } + else{ + piece.setState(PieceState.HOME); + } + + oldNode.clearOccupant(); + targetNode.setOccupant(piece); + + } + else{ + logic.addNotification(new HomeMoveNotification(piece.getUuid(), msg.getTargetIndex())); + int oldNoteIdx = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); + Node oldNode = logic.getGame().getBoard().getInfield()[oldNoteIdx]; + + //gets the targetNode + Node targetNode = logic.getGame().getActivePlayer().getHomeNodes()[msg.getTargetIndex()]; + + if (msg.getTargetIndex() ==logic.getGame().getActivePlayer().getHighestHomeIdx()) { + piece.setState(PieceState.HOMEFINISHED); + } + else{ + piece.setState(PieceState.HOME); + } + + oldNode.clearOccupant(); + targetNode.setOccupant(piece); + } + } + else { int oldIndex = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); Piece occ = logic.getGame().getBoard().getInfield()[msg.getTargetIndex()].getOccupant(); if (occ != null) { @@ -110,7 +141,17 @@ public void received(MoveMessage msg) { } //set new node logic.getGame().getBoard().getInfield()[msg.getTargetIndex()].setOccupant(piece); + if (logic.getGame().getBoard().getInfield()[msg.getTargetIndex()].isStart()){ + if (piece.isShielded()){ + piece.setShield(ShieldState.SUPPRESSED); + logic.addNotification(new ShieldSuppressedNotification(piece.getUuid())); + } + } else if (piece.isSuppressed()){ + piece.setShield(ShieldState.ACTIVE); + logic.addNotification(new ShieldActiveNotification(piece.getUuid())); + } } + System.out.println("send AnimationEndMessage"); logic.getGame().setTurboFlag(false); parent.setState(parent.getAnimation()); } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/determinestartplayerstate/Intro.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/determinestartplayerstate/Intro.java index 26ea3d3d..f3642f78 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/determinestartplayerstate/Intro.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/determinestartplayerstate/Intro.java @@ -4,6 +4,7 @@ import pp.mdga.client.ClientState; import pp.mdga.client.gamestate.DetermineStartPlayerState; import pp.mdga.game.Player; +import pp.mdga.game.card.PowerCard; import pp.mdga.message.client.AnimationEndMessage; import pp.mdga.notification.AcquireCardNotification; import pp.mdga.notification.ActivePlayerNotification; @@ -48,10 +49,12 @@ public void enter() { logic.getGame().getBoard().getInfield()[entry.getValue().getStartNodeIndex()].setOccupant(entry.getValue().getPieces()[0]); entry.getValue().getWaitingArea()[0] = null; animationCounter++; - if(entry.getKey() == logic.getOwnPlayerId()){ - logic.addNotification(new AcquireCardNotification(entry.getValue().getHandCards().get(0).getCard())); - } else { - logic.addNotification(new DrawCardNotification(entry.getValue().getColor(), entry.getValue().getHandCards().get(0).getCard())); + for (PowerCard card : entry.getValue().getHandCards()){ + if(entry.getKey() == logic.getOwnPlayerId()){ + logic.addNotification(new AcquireCardNotification(card.getCard())); + } else { + logic.addNotification(new DrawCardNotification(entry.getValue().getColor(), card.getCard())); + } } } } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/ChoosePieceState.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/ChoosePieceState.java index 57b7f257..226a150f 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/ChoosePieceState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/ChoosePieceState.java @@ -63,7 +63,7 @@ public void received(StartPieceMessage msg){ } @Override - public void received(NoTurnMessage msg){ + public void received(EndOfTurnMessage msg){ currentState.received(msg); } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/PlayPowerCardState.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/PlayPowerCardState.java index 1ecae283..cfd1fb00 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/PlayPowerCardState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/PlayPowerCardState.java @@ -3,6 +3,9 @@ import pp.mdga.client.ClientGameLogic; import pp.mdga.client.ClientState; import pp.mdga.client.gamestate.TurnState; +import pp.mdga.game.BonusCard; +import pp.mdga.game.card.ShieldCard; +import pp.mdga.game.card.SwapCard; import pp.mdga.message.client.AnimationEndMessage; import pp.mdga.message.server.PlayCardMessage; import pp.mdga.notification.PlayCardNotification; @@ -12,6 +15,7 @@ public class PlayPowerCardState extends TurnStates { private final TurnState parent; private PlayCardMessage playCardMessage; + private int extraAnimationCounter = 0; public PlayPowerCardState(ClientState parent, ClientGameLogic logic) { super(parent, logic); @@ -20,7 +24,12 @@ public PlayPowerCardState(ClientState parent, ClientGameLogic logic) { @Override public void enter() { - logic.addNotification(new PlayCardNotification(logic.getGame().getActiveColor() , playCardMessage.getCard().getCard())); + if(playCardMessage.getCard().getCard().equals(BonusCard.SWAP)) { + extraAnimationCounter++; + } + + logic.addNotification(new PlayCardNotification(logic.getGame().getActiveColor(), playCardMessage.getCard().getCard())); + logic.getGame().getActivePlayer().removeHandCard(playCardMessage.getCard()); handlePowerCard(playCardMessage); } @@ -35,6 +44,11 @@ public void setPlayCard(PlayCardMessage playCardMessage) { @Override public void selectAnimationEnd(){ + if(extraAnimationCounter > 0) { + extraAnimationCounter--; + return; + } + logic.send(new AnimationEndMessage()); parent.setState(parent.getRollDice()); } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/NoPieceState.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/NoPieceState.java index f43beea9..cb462f60 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/NoPieceState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/NoPieceState.java @@ -38,7 +38,6 @@ public void exit() { @Override public void received(SelectPieceMessage msg) { - //TODO ArrayList pieces = msg.getPieces().stream().map(piece -> logic.getGame().getPieceThroughUUID(piece.getUuid())).collect(Collectors.toCollection(ArrayList::new)); parent.getSelectPiece().setPossiblePieces(pieces); ArrayList listPiece = pieces.stream().map(Piece::getUuid).collect(Collectors.toCollection(ArrayList::new)); @@ -71,7 +70,7 @@ public void received(StartPieceMessage msg){ } @Override - public void received(NoTurnMessage msg){ + public void received(EndOfTurnMessage msg){ logic.getGame().setTurboFlag(false); parent.getParent().getParent().setState(parent.getParent().getParent().getWaiting()); } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/SelectPieceState.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/SelectPieceState.java index b85899b5..112f94da 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/SelectPieceState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/SelectPieceState.java @@ -4,11 +4,15 @@ import pp.mdga.client.ClientState; import pp.mdga.client.gamestate.turnstate.ChoosePieceState; import pp.mdga.game.Piece; +import pp.mdga.game.ShieldState; +import pp.mdga.game.PieceState; import pp.mdga.message.client.RequestMoveMessage; import pp.mdga.message.client.SelectedPiecesMessage; import pp.mdga.message.server.MoveMessage; import pp.mdga.notification.HomeMoveNotification; import pp.mdga.notification.MovePieceNotification; +import pp.mdga.notification.ShieldActiveNotification; +import pp.mdga.notification.ShieldSuppressedNotification; import pp.mdga.notification.ThrowPieceNotification; import java.util.ArrayList; @@ -49,11 +53,38 @@ public void selectPiece(Piece piece) { public void received(MoveMessage msg) { Piece piece = logic.getGame().getPieceThroughUUID(msg.getPiece().getUuid()); //logic.getGame().getBoard().getInfield()[logic.getGame().getBoard().getInfieldIndexOfPiece(piece)].clearOccupant(); + System.out.println("Client: selectPieceState: receivedMoveMessage: msg.isHomeMoved():" + msg.isHomeMove()); if (msg.isHomeMove()) { - logic.addNotification(new HomeMoveNotification(piece.getUuid(), msg.getTargetIndex())); - logic.getGame().getBoard().getInfield()[logic.getGame().getBoard().getInfieldIndexOfPiece(piece)].clearOccupant(); - logic.getGame().getPlayerByColor(piece.getColor()).setPieceInHome(msg.getTargetIndex(), piece); - } else { + System.out.println("Client: selectPieceState: receivedMoveMessage: msg.getPiece.getState():" + piece.getState()); + if (piece.getState().equals(PieceState.ACTIVE)) { + logic.addNotification(new HomeMoveNotification(piece.getUuid(), msg.getTargetIndex())); + int infieldIndex = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); + System.out.println("Client: SelectState: activePiece in Home: infieldIndex" + infieldIndex); + if (msg.getTargetIndex() == logic.getGame().getActivePlayer().getHighestHomeIdx()) { + piece.setState(PieceState.HOMEFINISHED); + } + else { + piece.setState(PieceState.HOME); + } + logic.getGame().getBoard().getInfield()[infieldIndex].clearOccupant(); + logic.getGame().getPlayerByColor(piece.getColor()).setPieceInHome(msg.getTargetIndex(), piece); + } + else { + System.out.println("Client: SelectPieceState: receivedMoveMessage:reached else"); + logic.addNotification(new HomeMoveNotification(piece.getUuid(), msg.getTargetIndex())); + System.out.println("Client: electPieceState: homeindex" + logic.getGame().getActivePlayer().getHomeIndexOfPiece(piece)); + int pieceHomeIndex = logic.getGame().getActivePlayer().getHomeIndexOfPiece(piece); + if (msg.getTargetIndex() == logic.getGame().getActivePlayer().getHighestHomeIdx()) { + piece.setState(PieceState.HOMEFINISHED); + } + else { + piece.setState(PieceState.HOME); + } + logic.getGame().getActivePlayer().getHomeNodes()[pieceHomeIndex].clearOccupant(); + logic.getGame().getPlayerByColor(piece.getColor()).setPieceInHome(msg.getTargetIndex(), piece); + } + } + else { int oldIndex = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); Piece occ = logic.getGame().getBoard().getInfield()[msg.getTargetIndex()].getOccupant(); @@ -70,6 +101,16 @@ public void received(MoveMessage msg) { logic.getGame().getBoard().getInfield()[logic.getGame().getBoard().getInfieldIndexOfPiece(piece)].clearOccupant(); //set new node logic.getGame().getBoard().getInfield()[msg.getTargetIndex()].setOccupant(piece); + if (logic.getGame().getBoard().getInfield()[msg.getTargetIndex()].isStart()) { + if (piece.isShielded()) { + piece.setShield(ShieldState.SUPPRESSED); + logic.addNotification(new ShieldSuppressedNotification(piece.getUuid())); + } + } + else if (piece.isSuppressed()) { + piece.setShield(ShieldState.ACTIVE); + logic.addNotification(new ShieldActiveNotification(piece.getUuid())); + } } logic.getGame().setTurboFlag(false); parent.getParent().setState(parent.getParent().getMovePiece()); diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/StartPieceState.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/StartPieceState.java index 9594e356..1ad5972b 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/StartPieceState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/choosepiecestate/StartPieceState.java @@ -5,10 +5,14 @@ import pp.mdga.client.gamestate.turnstate.ChoosePieceState; import pp.mdga.game.Node; import pp.mdga.game.Piece; +import pp.mdga.game.ShieldState; import pp.mdga.message.client.RequestMoveMessage; import pp.mdga.message.client.SelectedPiecesMessage; import pp.mdga.message.server.MoveMessage; import pp.mdga.notification.MovePieceNotification; +import pp.mdga.notification.RemoveShieldNotification; +import pp.mdga.notification.ShieldActiveNotification; +import pp.mdga.notification.ShieldSuppressedNotification; import pp.mdga.notification.ThrowPieceNotification; import java.util.ArrayList; @@ -63,6 +67,17 @@ public void received(MoveMessage msg){ logic.addNotification(new ThrowPieceNotification(occ.getUuid(), piece.getColor())); } + if (targetNode.isStart()){ + if (piece.isShielded()){ + piece.setShield(ShieldState.SUPPRESSED); + logic.addNotification(new ShieldSuppressedNotification(piece.getUuid())); + } + } else if (piece.isSuppressed()){ + piece.setShield(ShieldState.ACTIVE); + logic.addNotification(new RemoveShieldNotification(piece.getUuid())); + logic.addNotification(new ShieldActiveNotification(piece.getUuid())); + } + targetNode.setOccupant(msg.getPiece()); logic.addNotification(new MovePieceNotification(msg.getPiece().getUuid(), oldIndex, targetIndex)); logic.getGame().setTurboFlag(false); diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/powercardstate/ChoosePowerCardState.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/powercardstate/ChoosePowerCardState.java index 59ce519d..7b22da92 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/powercardstate/ChoosePowerCardState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/powercardstate/ChoosePowerCardState.java @@ -5,6 +5,7 @@ import pp.mdga.client.gamestate.turnstate.PowerCardState; import pp.mdga.game.BonusCard; import pp.mdga.game.Piece; +import pp.mdga.game.Player; import pp.mdga.game.card.*; import pp.mdga.message.client.NoPowerCardMessage; import pp.mdga.message.client.SelectCardMessage; @@ -73,8 +74,14 @@ public void received(PossibleCardsMessage msg){ */ @Override public void selectCard(BonusCard card){ + Player player = logic.getGame().getPlayers().get(logic.getOwnPlayerId()); + ArrayList handCards = player.getHandCards(); if(card != null){ - logic.send(new SelectCardMessage(logic.getGame().getPlayers().get(logic.getOwnPlayerId()).getPowerCardByType(card))); + PowerCard select = player.getPowerCardByType(card); + if(select == null){ + select = select; + } + logic.send(new SelectCardMessage(select)); } else { logic.send(new NoPowerCardMessage()); } @@ -112,7 +119,6 @@ public void received(PossiblePieceMessage msg){ if (msg.getEnemyPossiblePieces().isEmpty()){ parent.getShield().setPossiblePieces(msg.getOwnPossiblePieces().stream().map(piece -> logic.getGame().getPieceThroughUUID(piece.getUuid())).collect(Collectors.toCollection(ArrayList::new))); parent.setState(parent.getShield()); - logic.addNotification(new SelectableShieldNotification(msg.getOwnPossiblePieces().stream().map(Piece::getUuid).toList())); } else { System.out.println("Should enter Swap State"); parent.getSwap().setPossibleOwnPieces(msg.getOwnPossiblePieces().stream().map(piece -> logic.getGame().getPieceThroughUUID(piece.getUuid())).collect(Collectors.toCollection(ArrayList::new))); diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/powercardstate/ShieldState.java b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/powercardstate/ShieldState.java index 95a53dd0..87882f2a 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/powercardstate/ShieldState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/client/gamestate/turnstate/powercardstate/ShieldState.java @@ -7,6 +7,7 @@ import pp.mdga.message.client.RequestPlayCardMessage; import pp.mdga.message.client.SelectedPiecesMessage; import pp.mdga.message.server.PlayCardMessage; +import pp.mdga.notification.SelectableShieldNotification; import java.lang.System.Logger.Level; import java.util.ArrayList; @@ -27,8 +28,7 @@ public ShieldState(ClientState parent, ClientGameLogic logic) { @Override public void enter() { - logic.addNotification(null); - //TODO: selectable piece notification + logic.addNotification(new SelectableShieldNotification(possiblePieces.stream().map(Piece::getUuid).toList())); } @Override diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/game/Die.java b/Projekte/mdga/model/src/main/java/pp/mdga/game/Die.java index c3b99cf5..dc8a026e 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/game/Die.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/game/Die.java @@ -18,17 +18,17 @@ public class Die { /** * The probability of rolling a zero eye. */ - public static final double ZERO_EYE = 0.2; + public static final double ZERO_EYE = 0; /** * The probability of rolling a normal eye. */ - public static final double NORMAL_EYE = 0.2; + public static final double NORMAL_EYE = 0; /** * The probability of rolling a double eye. */ - public static final double DOUBLE_EYE = 0.6; + public static final double DOUBLE_EYE = 1; /** * The modifier applied to the die roll. diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/game/Game.java b/Projekte/mdga/model/src/main/java/pp/mdga/game/Game.java index e7e06348..1a151a0f 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/game/Game.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/game/Game.java @@ -87,15 +87,15 @@ public Game() { gameStatistics = new Statistic(); initializeDrawPile(); board = new Board(); - die = new Die(2,1,6,2,1,3); + die = new Die(1,4); } /** * This method initializes the draw pile with the predefined number of bonus cards. */ private void initializeDrawPile() { -// this.addBonusCards(new TurboCard(), AMOUNT_OF_TURBO_CARDS); - this.addBonusCards(new SwapCard(), AMOUNT_OF_SWAP_CARDS); + this.addBonusCards(new TurboCard(), AMOUNT_OF_TURBO_CARDS); +// this.addBonusCards(new SwapCard(), AMOUNT_OF_SWAP_CARDS); // this.addBonusCards(new ShieldCard(), AMOUNT_OF_SHIELD_CARDS); Collections.shuffle(this.drawPile); } @@ -107,9 +107,13 @@ private void initializeDrawPile() { */ public PowerCard draw() { if (!this.drawPile.isEmpty()) { + if (drawPile.size() == 1){ + Collections.shuffle(this.discardPile); + this.drawPile.addAll(this.discardPile); + discardPile.clear(); + } return this.drawPile.remove(0); } - return null; } @@ -210,6 +214,15 @@ public Player getPlayerByColor(Color color) { return null; } + /** + * This method will be used to the get the active player + * + * @return the active player + */ + public Player getActivePlayer(){ + return getPlayerByColor(activeColor); + } + /** * This method will be used to return all connected players as a list. * diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/game/Node.java b/Projekte/mdga/model/src/main/java/pp/mdga/game/Node.java index 0dc1d98a..604ef1cd 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/game/Node.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/game/Node.java @@ -43,9 +43,6 @@ public Piece getOccupant() { * @param occupant the new occupant of the node */ public void setOccupant(Piece occupant) { - if (occupant.isSuppressed()) { - occupant.setShield(ShieldState.NONE); - } this.occupant = occupant; } @@ -99,4 +96,8 @@ public boolean isOccupied() { public boolean isOccupied(Color color) { return isOccupied() && this.occupant.getColor() == color; } + + public boolean isStart() { + return false; + } } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/game/Player.java b/Projekte/mdga/model/src/main/java/pp/mdga/game/Player.java index e7b8aa2e..bd7f14f6 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/game/Player.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/game/Player.java @@ -152,6 +152,7 @@ public PowerCard getPowerCardByType(BonusCard bonusCard) { } } return null; +// throw new RuntimeException("bonusCard is not in handCards"); } public Piece getWaitingPiece(){ @@ -205,6 +206,22 @@ public boolean isHomeFinished(Piece piece) { return true; } + /** + * this method will be used to determine the highest index in the home + * + * @return the index + */ + public int getHighestHomeIdx(){ + for (int i =3; i>=0;i--){ + if(!homeNodes[i].isOccupied()) { + System.out.println("Player: highestHomeIndex:"+i); + return i; + } + + } + return -1; + } + /** * This method returns the give name of the Player * diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/game/StartNode.java b/Projekte/mdga/model/src/main/java/pp/mdga/game/StartNode.java index 0033738f..5a62eaba 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/game/StartNode.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/game/StartNode.java @@ -47,4 +47,9 @@ public Color getColor() { public void setColor(Color color) { this.color = color; } + + @Override + public boolean isStart() { + return true; + } } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/message/server/SpectatorMessage.java b/Projekte/mdga/model/src/main/java/pp/mdga/message/server/SpectatorMessage.java index b7cc8890..acc76a36 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/message/server/SpectatorMessage.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/message/server/SpectatorMessage.java @@ -1,8 +1,11 @@ package pp.mdga.message.server; +import com.jme3.network.serializing.Serializable; + /** * A message sent by the server to indicate that the client is now a spectator. */ +@Serializable public class SpectatorMessage extends ServerMessage { /** * Constructor diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/GameState.java b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/GameState.java index 8e5e955a..4d856635 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/GameState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/GameState.java @@ -37,7 +37,6 @@ public GameState(ServerGameLogic logic) { this.determineStartPlayerState = new DetermineStartPlayerState(this, logic); this.animationState = new AnimationState(this, logic); this.turnState = new TurnState(this, logic); - this.setCurrentState(this.determineStartPlayerState); } /** @@ -46,6 +45,7 @@ public GameState(ServerGameLogic logic) { @Override public void enter() { LOGGER.log(System.Logger.Level.DEBUG, "Entered GameState state."); + this.setCurrentState(this.determineStartPlayerState); } /** diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/LobbyState.java b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/LobbyState.java index 9ae89659..d0c2995c 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/LobbyState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/LobbyState.java @@ -4,6 +4,10 @@ import pp.mdga.game.Piece; import pp.mdga.game.PieceState; import pp.mdga.game.Player; +import pp.mdga.game.card.PowerCard; +import pp.mdga.game.card.ShieldCard; +import pp.mdga.game.card.SwapCard; +import pp.mdga.game.card.TurboCard; import pp.mdga.message.client.*; import pp.mdga.message.server.*; import pp.mdga.server.ServerGameLogic; @@ -52,6 +56,39 @@ public void initializeGame() { for (var player : this.logic.getGame().getPlayers().values()) { player.initialize(); player.addHandCard(this.logic.getGame().draw()); + //TODO + player.addHandCard(new ShieldCard()); + player.addHandCard(new ShieldCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + player.addHandCard(new TurboCard()); + + player.addHandCard(new SwapCard()); + player.addHandCard(new SwapCard()); + + Piece piece = player.getPieces()[0]; player.getWaitingArea()[0] = null; piece.setState(PieceState.ACTIVE); diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/DetermineStartPlayerState.java b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/DetermineStartPlayerState.java index 0e3816d9..d1481445 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/DetermineStartPlayerState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/DetermineStartPlayerState.java @@ -30,8 +30,10 @@ public class DetermineStartPlayerState extends GameAutomatonState { * Create DetermineStartPlayerState attributes. */ private final Map diceResults = new HashMap<>(); + private final Map finalDiceResults = new HashMap<>(); private final List playersHaveToRoll = new ArrayList<>(); private final Set messageReceived = new HashSet<>();; + private int playerToStart; /** * Constructs a server state of the specified game logic. @@ -45,12 +47,13 @@ public DetermineStartPlayerState(GameState gameAutomaton, ServerGameLogic logic) @Override public void enter() { - LOGGER.log(System.Logger.Level.DEBUG, "Entered DetermineStartPlayerState state."); + LOGGER.log(System.Logger.Level.INFO, "Entered DetermineStartPlayerState state."); + playerToStart = this.logic.getGame().getPlayers().size(); } @Override public void exit() { - LOGGER.log(System.Logger.Level.DEBUG, "Exited DetermineStartPlayerState state."); + LOGGER.log(Level.INFO, "Exited DetermineStartPlayerState state."); this.diceResults.clear(); this.messageReceived.clear(); } @@ -67,23 +70,21 @@ public void received(RequestDieMessage msg, int from) { int roll = this.logic.getGame().getDie().shuffle(); this.logic.getServerSender().send(from, new DieMessage(roll)); this.diceResults.put(from, roll); - if (this.diceResults.size() == this.logic.getGame().getPlayers().size()) { + if (this.diceResults.size() == playerToStart) { int maximumRoll = 0; for (Map.Entry entry : this.diceResults.entrySet()) { if (maximumRoll == entry.getValue()) { this.playersHaveToRoll.add(entry.getKey()); + LOGGER.log(Level.INFO, "Players have to roll(RD same as maximum): {0}", this.playersHaveToRoll.size()); } else if (maximumRoll < entry.getValue()) { maximumRoll = entry.getValue(); this.playersHaveToRoll.clear(); this.playersHaveToRoll.add(entry.getKey()); + LOGGER.log(Level.INFO, "Players have to roll(RD higher as maximum): {0}", this.playersHaveToRoll.size()); } } - - for (int id: this.playersHaveToRoll) { - this.diceResults.remove(id); - } } } @@ -97,18 +98,24 @@ else if (maximumRoll < entry.getValue()) { @Override public void received(AnimationEndMessage msg, int from) { this.messageReceived.add(from); - if (this.messageReceived.size() == this.logic.getGame().getPlayers().size()) { + if (this.messageReceived.size() == playerToStart) { this.messageReceived.clear(); + LOGGER.log(Level.INFO, "Players have to roll(Animation End): {0}", this.playersHaveToRoll.size()); if (this.playersHaveToRoll.size() > 1) { + playerToStart = this.playersHaveToRoll.size(); for (Integer id : this.playersHaveToRoll) { + diceResults.remove(id); this.logic.getServerSender().send(id, new DiceNowMessage()); } + finalDiceResults.putAll(this.diceResults); + diceResults.clear(); } else { + finalDiceResults.putAll(this.diceResults); LOGGER.log(Level.INFO, "Players have to roll: %s".formatted(this.logic.getGame().getPlayerById(this.playersHaveToRoll.get(0)))); Color color = this.logic.getGame().getPlayerById(this.playersHaveToRoll.get(0)).getColor(); this.logic.getGame().setActiveColor(color); - this.logic.getServerSender().broadcast(new RankingResponseMessage(this.diceResults)); + this.logic.getServerSender().broadcast(new RankingResponseMessage(this.finalDiceResults)); this.logic.getServerSender().broadcast(new ActivePlayerMessage(color)); this.gameAutomaton.setCurrentState(this.gameAutomaton.getAnimationState()); } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/TurnState.java b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/TurnState.java index 464b0e70..18a6d457 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/TurnState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/TurnState.java @@ -195,6 +195,7 @@ public void setCurrentState(TurnAutomatonState state) { if (this.currentState != null) { this.currentState.exit(); } + System.out.println("Server: the server entered:"+state); this.currentState = state; this.currentState.enter(); } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/ChoosePieceAutomatonState.java b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/ChoosePieceAutomatonState.java index 48fe982a..eb231422 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/ChoosePieceAutomatonState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/ChoosePieceAutomatonState.java @@ -17,86 +17,181 @@ public abstract class ChoosePieceAutomatonState extends ServerState { * Constructs a server state of the specified game logic. * * @param choosePieceAutomaton as the automaton of the choose piece state as a ChoosePieceState object. - * @param logic the game logic + * @param logic the game logic */ public ChoosePieceAutomatonState(ChoosePieceState choosePieceAutomaton, ServerGameLogic logic) { super(logic); this.choosePieceAutomaton = choosePieceAutomaton; } - protected boolean canMove(Piece piece){ + /** + * returns true, if the piece can move inside the home or infield or move from the infield to the home + * + * @param piece the piece that will be checked + * @return true, if the piece can move + */ + protected boolean canMove(Piece piece) { + System.out.println("Server: reached canMove() for piece: " + piece); int steps = logic.getGame().getDiceModifier() * logic.getGame().getDiceEyes(); - if (piece.getState().equals(PieceState.HOME)){ - return canHomeMove(piece, steps); - } else { - int homeMoves = getHomeMoves(piece, steps); - if (homeMoves > 0){ - return canHomeMove(piece, homeMoves); - } else { - return canInfieldMove(piece, steps); - } - } - } + int pieceIdx = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); + int startIdx = logic.getGame().getActivePlayer().getStartNodeIndex(); + int normPieceIdx = (-startIdx + pieceIdx + 40) % 40; + int targetIdx = normPieceIdx + steps; - protected int getHomeMoves(Piece piece, int steps){ - int pieceIndex = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); - Color color = piece.getColor(); - int startIndex = logic.getGame().getPlayerByColor(color).getStartNodeIndex(); - int moveIndex = pieceIndex + steps; - if (moveIndex > logic.getGame().getBoard().getInfield().length){ - if (startIndex > pieceIndex){ - return steps - (startIndex - pieceIndex -1); + //checks if the piece can move in the home + if (piece.getState().equals(PieceState.HOME)) { + if (canPieceMoveInHome(piece, steps)) { + return true; } - moveIndex %= logic.getGame().getBoard().getInfield().length; - if (moveIndex >= startIndex){ - return moveIndex - startIndex + 1; + } + else { + if (canPieceMoveInHome(piece, steps)) { + return true; } - return 0; - } - if (pieceIndex < startIndex && startIndex <= moveIndex){ - return moveIndex - startIndex + 1; - } - return 0; - } - - private boolean canInfieldMove(Piece piece, int steps){ - int pieceIndex = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); - int moveIndex = (pieceIndex + steps) % logic.getGame().getBoard().getInfield().length; - Piece occupant = logic.getGame().getBoard().getInfield()[moveIndex].getOccupant(); - if (occupant != null){ - if (occupant.isShielded()){ - return false; - } - return occupant.getColor() != piece.getColor(); - } - return true; - } - - private boolean canHomeMove(Piece piece, int moveIndex){ - Color color = piece.getColor(); - Player player = logic.getGame().getPlayerByColor(color); - Node[] homeNodes = player.getHomeNodes(); - int index; - if (player.pieceInsideOfHome(piece)){ - index = player.getHomeIndexOfPiece(piece); - } else { - index = 0; - } - if (index + moveIndex >= homeNodes.length){ - return false; - } else { - for (int i = index; i <= index + moveIndex; i++){ - if(homeNodes[i].isOccupied()){ - return false; + //checks if the piece will not go over its home-field + else if (40 > targetIdx && (!piece.getState().equals(PieceState.HOME) || !piece.getState().equals(PieceState.HOMEFINISHED))) { + Color activeColor = logic.getGame().getActiveColor(); + Node tartgetNode = logic.getGame().getBoard().getInfield()[(pieceIdx + steps) % 40]; + //checks if the target-node is not occupied by an own color + if (!tartgetNode.isOccupied(activeColor)) { + //checks if the targetNode is not occupied or the occupant ha no shield + if (!tartgetNode.isOccupied() || tartgetNode.getOccupant().getShield() != ShieldState.ACTIVE) { + return true; + } } } - return true; + //returns false it the piece can't move + return false; + } + return false; + } + + /** + * tests if the piece can move in the home or inside the home + * + * @param piece + * @param steps + * @return false, if the piece can't move in the home + */ + protected boolean canPieceMoveInHome(Piece piece, int steps) { + //tests if the piece can move inside the home + steps = logic.getGame().getDiceModifier() * logic.getGame().getDiceEyes(); + System.out.println("Server: reached canPieceMoveInHome for piece: " + piece + " and the steps: " + steps); + + if (piece.getState().equals(PieceState.HOME)) { + int homeIdx = logic.getGame().getActivePlayer().getHomeIndexOfPiece(piece); + System.out.println("Server: reached canPieceMoveInHome for piece: " + piece + " and the steps: " + steps + " and the homeIndex: " + homeIdx + " and the if-clause ((3 - homeIdx) >= steps - 1): " + ((3 - homeIdx) >= steps - 1)); + //tests if the steps are less than the possible movement + if ((3 - homeIdx) >= steps - 1) { + return !jumpOver(steps, homeIdx, false); + } + else { + return false; + } + } + //tests if the piece can move in the home + else if (piece.getState() == PieceState.ACTIVE) { + int pieceIdx = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); + int startIdx = logic.getGame().getActivePlayer().getStartNodeIndex(); + int normPieceIdx = (-startIdx + pieceIdx + 40) % 40; + int targetIdx = normPieceIdx + steps; + System.out.println("Server: canPieceHomeMove: else: Active: with pieceIndex: " + pieceIdx + " and the steps: " + steps + " and startIdx: " + startIdx + " and targetIdx: " + targetIdx + " and the if-statement (targetIdx >= 40): " + (targetIdx >= 40)); + if (targetIdx >= 40) { + int stepsToHome = 39 - normPieceIdx; + int restMovement = steps - stepsToHome - 1; + System.out.println("Server: canPieceHomeMove:else: restMovement: " + restMovement + " and the if-clause(restMovement >= 3):" + (restMovement >= 3)); + if (restMovement >= 4) return false; + return !jumpOver(restMovement, 0, true); + } + } + else { + return false; + } + return false; + } + + /** + * tests if the piece, when moved in or inside a home, must jump over another piece + * + * @param stepsInHome the steps walked inside the home + * @param homeIdx the index of the piece inside, or 0 if come from outside + * @param outside a boolean, if the piece moves inside a house or in a house + * @return false, if there is no piece to jump over + */ + private boolean jumpOver(int stepsInHome, int homeIdx, boolean outside) { + //tests if the piece comes from the outside in the home + if (outside) { + System.out.println("Server: jumpOver: for the homeIndex: " + homeIdx + " ,stepsInHome: " + stepsInHome + " , outside: " + outside + " annd the targetIndex: " + stepsInHome); + if (logic.getGame().getActivePlayer().getHomeNodes()[stepsInHome].isOccupied()) return true; + for (int i = 0; i <= stepsInHome; i++) { + if (logic.getGame().getActivePlayer().getHomeNodes()[i].isOccupied()) return true; + } + } + //tests if the piece jumps over a piece from inside the home + else { + int targetIndex = stepsInHome + homeIdx; + System.out.println("Server: jumpOver: for the homeIndex: " + homeIdx + " ,stepsInHome: " + stepsInHome + " , outside: " + outside + " and the targetIndex: " + targetIndex); + if (logic.getGame().getActivePlayer().getHomeNodes()[targetIndex].isOccupied()) return true; + for (int i = 1 + homeIdx; i <= targetIndex; i++) { + if (logic.getGame().getActivePlayer().getHomeNodes()[i].isOccupied()) return true; + } + } + return false; + } + + /** + * returns the index in the home, where the piece will go in the home + * + * @param piece the give piece + * @return the index in the home, where the piece will go + */ + protected int getHomeTargetIdx(Piece piece, int steps) { + //tests if the piece is active and move in the house + if (piece.getState() == PieceState.ACTIVE) { + //gets the id's + int pieceIdx = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); + int startIdx = logic.getGame().getActivePlayer().getStartNodeIndex(); + //normalize the idx + int normPieceIdx = (-startIdx + pieceIdx + 40) % 40; + //calculate the steps to the home + int stepsToHome = 39 - normPieceIdx; + //calculates the rest-movement inside a home + int restMovement = steps - stepsToHome - 1; + System.out.println("Server: getHomeTargetIndex for the piece: " + piece + " with the index: " + restMovement); + return restMovement; + } + //the else handles the logic if the piece is in the home and moves inside the house + else { + int pieceHomeIdx = logic.getGame().getActivePlayer().getHomeIndexOfPiece(piece); + System.out.println("Server: getHomeTargetIndex for the piece: " + piece + " with the index: " + (pieceHomeIdx + steps)); + return pieceHomeIdx + steps; } } - protected int calculateTargetIndex(Piece piece){ - int steps = logic.getGame().getDiceModifier() * logic.getGame().getDiceEyes(); + /** + * returns the target index inside the infield + * + * @param piece the piece given + * @return the index in the infield + */ + protected int getInfieldTarget(Piece piece, int steps) { + int index = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); + System.out.println("Server: calculated the targetIndex in the Infield for:" + piece + "with the value" + ((steps + index) % 40)); + return (steps + index) % 40; + } - return (logic.getGame().getBoard().getInfieldIndexOfPiece(piece) + steps) % logic.getGame().getBoard().getInfield().length; + /** + * this method is used for calculating the targetIndex + * + * @param piece the piece give + * @return the index + */ + protected int calculateTargetIndex(Piece piece) { + int steps = logic.getGame().getDiceModifier() * logic.getGame().getDiceEyes(); + if (canPieceMoveInHome(piece, steps)) { + System.out.println("Server: ChoosePieceStateAutomaton: calculate index in home:" + getHomeTargetIdx(piece, steps)); + return getHomeTargetIdx(piece, steps); + } + return getInfieldTarget(piece, steps); } } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/NoPieceState.java b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/NoPieceState.java index 1a15946f..4d80be7a 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/NoPieceState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/NoPieceState.java @@ -24,48 +24,52 @@ public NoPieceState(ChoosePieceState choosePieceAutomaton, ServerGameLogic logic super(choosePieceAutomaton, logic); } - private void initialize(){ + private void initialize() { Player activePlayer = logic.getGame().getPlayerByColor(logic.getGame().getActiveColor()); - if(logic.getGame().getDiceModifier() == 0){ + if (logic.getGame().getDiceModifier() == 0) { if (logic.getGame().getDiceEyes() == 6) { - if (activePlayer.hasPieceInWaitingArea()){ - if (!logic.getGame().getBoard().getInfield()[activePlayer.getStartNodeIndex()].isOccupied(activePlayer.getColor())){ - this.choosePieceAutomaton.setCurrentState(this.choosePieceAutomaton.getWaitingPieceState()); - } else { - this.choosePieceAutomaton.setCurrentState(this.choosePieceAutomaton.getNoTurnState()); + if (activePlayer.hasPieceInWaitingArea()) { + if (!logic.getGame().getBoard().getInfield()[activePlayer.getStartNodeIndex()].isOccupied(activePlayer.getColor())) { + this.choosePieceAutomaton.setCurrentState(this.choosePieceAutomaton.getWaitingPieceState()); + return; } - } else { - this.choosePieceAutomaton.setCurrentState(this.choosePieceAutomaton.getNoTurnState()); } } - } else if (activePlayer.hasPieceInWaitingArea()) { - if (!logic.getGame().getBoard().getInfield()[activePlayer.getStartNodeIndex()].isOccupied(activePlayer.getColor())){ + this.choosePieceAutomaton.setCurrentState(this.choosePieceAutomaton.getNoTurnState()); + } + else if (activePlayer.hasPieceInWaitingArea()) { + if (!logic.getGame().getBoard().getInfield()[activePlayer.getStartNodeIndex()].isOccupied(activePlayer.getColor())) { if (logic.getGame().getDiceEyes() == 6) { this.choosePieceAutomaton.setCurrentState(this.choosePieceAutomaton.getWaitingPieceState()); - } else { + } + else { checkSelectPiece(activePlayer); } - } else if (canMove(logic.getGame().getBoard().getInfield()[activePlayer.getStartNodeIndex()].getOccupant())){ + } + else if (canMove(logic.getGame().getBoard().getInfield()[activePlayer.getStartNodeIndex()].getOccupant())) { this.choosePieceAutomaton.setCurrentState(this.choosePieceAutomaton.getStartPieceState()); - } else { + } + else { checkSelectPiece(activePlayer); } - } else { + } + else { checkSelectPiece(activePlayer); } } - private void checkSelectPiece(Player activePlayer){ + private void checkSelectPiece(Player activePlayer) { ArrayList moveablePieces = new ArrayList<>(); - for (Piece piece : activePlayer.getPieces()){ - if (piece.getState().equals(PieceState.ACTIVE) || piece.getState().equals(PieceState.HOME)){ + for (Piece piece : activePlayer.getPieces()) { + if (piece.getState().equals(PieceState.ACTIVE) || piece.getState().equals(PieceState.HOME)) { moveablePieces.add(piece); } } moveablePieces.removeIf(piece -> !canMove(piece)); if (moveablePieces.isEmpty()) { this.choosePieceAutomaton.setCurrentState(this.choosePieceAutomaton.getNoTurnState()); - } else { + } + else { this.choosePieceAutomaton.getSelectPieceState().setMoveablePieces(moveablePieces); this.choosePieceAutomaton.setCurrentState(this.choosePieceAutomaton.getSelectPieceState()); } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/NoTurnState.java b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/NoTurnState.java index 368088a4..94463566 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/NoTurnState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/NoTurnState.java @@ -25,10 +25,11 @@ public NoTurnState(ChoosePieceState choosePieceAutomaton, ServerGameLogic logic) private void setActivePlayer(Color color) { if (!logic.getGame().getPlayerByColor(color.next(logic.getGame())).isFinished()) { logic.getGame().setActiveColor(logic.getGame().getActiveColor().next(logic.getGame())); - logic.getServerSender().broadcast(new ActivePlayerMessage(color.next(logic.getGame()))); + logic.getServerSender().broadcast(new ActivePlayerMessage(logic.getGame().getActiveColor())); } else { setActivePlayer(color.next(logic.getGame())); } + this.choosePieceAutomaton.getTurnAutomaton().getGameAutomaton().setCurrentState(this.choosePieceAutomaton.getTurnAutomaton().getGameAutomaton().getTurnState()); } /** diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/SelectPieceState.java b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/SelectPieceState.java index 3dd0e330..5ea55e43 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/SelectPieceState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/SelectPieceState.java @@ -2,6 +2,7 @@ import pp.mdga.game.*; import pp.mdga.game.card.HiddenCard; +import pp.mdga.game.card.PowerCard; import pp.mdga.message.client.RequestMoveMessage; import pp.mdga.message.server.DrawCardMessage; import pp.mdga.message.server.MoveMessage; @@ -40,65 +41,111 @@ public void setMoveablePieces(ArrayList moveablePieces) { */ @Override public void enter() { - LOGGER.log(System.Logger.Level.DEBUG, "Entered SelectPieceState state."); int steps = logic.getGame().getDiceModifier() * logic.getGame().getDiceEyes(); for (Piece piece : moveablePieces) { - int homeMoves = getHomeMoves(piece, steps); - if (homeMoves > 0) { + + if (canPieceMoveInHome(piece, steps)) { + int target = getHomeTargetIdx(piece, steps); + targetIndex.add(target); isHomeMove.add(true); - targetIndex.add(homeMoves); - } else { + } + else { + int target = getInfieldTarget(piece, steps); + targetIndex.add(target); isHomeMove.add(false); - targetIndex.add(calculateTargetIndex(piece)); } } logic.getServerSender().send(logic.getGame().getActivePlayerId(), new SelectPieceMessage(moveablePieces, isHomeMove, targetIndex)); } @Override - public void received(RequestMoveMessage msg, int from){ - if(!moveablePieces.contains(msg.getPiece())){ + public void received(RequestMoveMessage msg, int from) { + if (!moveablePieces.contains(msg.getPiece())) { throw new RuntimeException("invalid Piece"); } int indexOfPiece = moveablePieces.indexOf(msg.getPiece()); - Piece movePiece = moveablePieces.get(indexOfPiece); - boolean homeMove = isHomeMove.get(indexOfPiece); - int targIdx = targetIndex.get(indexOfPiece); + int steps = logic.getGame().getDiceModifier() * logic.getGame().getDiceEyes(); + Piece piece = moveablePieces.get(indexOfPiece); + if (canPieceMoveInHome(piece, steps)) { + if (piece.getState().equals(PieceState.HOME)) { + //gets the oldNode + int homeIndex = logic.getGame().getActivePlayer().getHomeIndexOfPiece(piece); + Node oldNode = logic.getGame().getActivePlayer().getHomeNodes()[homeIndex]; + //gets the targetNode + int targetHomeIdx = getHomeTargetIdx(piece, steps); + Node targetNode = logic.getGame().getActivePlayer().getHomeNodes()[targetHomeIdx]; + if (targetHomeIdx == logic.getGame().getActivePlayer().getHighestHomeIdx()) { + piece.setState(PieceState.HOMEFINISHED); + } + else { + piece.setState(PieceState.HOME); + } - Node oldNode = logic.getGame().getBoard().getInfield()[logic.getGame().getBoard().getInfieldIndexOfPiece(movePiece)]; - oldNode.clearOccupant(); - if (homeMove) { - //setPieceInHome - logic.getGame().getPlayerByColor(msg.getPiece().getColor()).setPieceInHome(targIdx, movePiece); - - if (logic.getGame().getPlayerByColor(msg.getPiece().getColor()).isHomeFinished(logic.getGame().getPieceThroughUUID(msg.getPiece().getUuid()))) { - movePiece.setState(PieceState.HOMEFINISHED); + oldNode.clearOccupant(); + targetNode.setOccupant(piece); } else { - movePiece.setState(PieceState.HOME); - } - movePiece.setShield(ShieldState.NONE); - } else { - Node targetNode = logic.getGame().getBoard().getInfield()[targIdx]; + int oldNoteIdx = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); + Node oldNode = logic.getGame().getBoard().getInfield()[oldNoteIdx]; - if(targetNode.isBonus()) { - for (Player p : logic.getGame().getPlayersAsList()) { - if(p.getColor() == logic.getGame().getActiveColor()) { - logic.getServerSender().send(logic.getGame().getPlayerIdByColor(p.getColor()), new DrawCardMessage(logic.getGame().draw())); - } else { - logic.getServerSender().send(logic.getGame().getPlayerIdByColor(p.getColor()), new DrawCardMessage(new HiddenCard())); - } + //gets the targetNode + int targetHomeIdx = getHomeTargetIdx(piece, steps); + Node targetNode = logic.getGame().getActivePlayer().getHomeNodes()[targetHomeIdx]; + + if (targetHomeIdx == logic.getGame().getActivePlayer().getHighestHomeIdx()) { + piece.setState(PieceState.HOMEFINISHED); } + else { + piece.setState(PieceState.HOME); + } + + oldNode.clearOccupant(); + targetNode.setOccupant(piece); } + LOGGER.log(System.Logger.Level.INFO, "Server : SelectPieceState: PieceState:" + piece.getState()); + } + else { + LOGGER.log(System.Logger.Level.INFO, "Server : SelectPieceState: PieceState:" + piece.getState()); + int oldNoteIdx = logic.getGame().getBoard().getInfieldIndexOfPiece(piece); + Node oldNode = logic.getGame().getBoard().getInfield()[oldNoteIdx]; + + int targetIndex = (oldNoteIdx + steps) % 40; + Node targetNode = logic.getGame().getBoard().getInfield()[targetIndex]; Piece occ = targetNode.getOccupant(); if (occ != null) { logic.getGame().getPlayerByColor(occ.getColor()).addWaitingPiece(occ); } - targetNode.setOccupant(msg.getPiece()); + + if (targetNode.isStart()) { + if (piece.getShield() == ShieldState.ACTIVE) piece.setShield(ShieldState.SUPPRESSED); + } + + oldNode.clearOccupant(); + targetNode.setOccupant(piece); + } + + boolean homeMove = isHomeMove.get(indexOfPiece); + int targIdx = targetIndex.get(indexOfPiece); + + Node targetNode = logic.getGame().getBoard().getInfield()[targIdx]; + + LOGGER.log(System.Logger.Level.INFO, "Server : SelectPieceState: PieceState: end:" + piece.getState()); + logic.getServerSender().broadcast(new MoveMessage(piece, homeMove, targIdx)); + + if (targetNode.isBonus()) { + for (Player p : logic.getGame().getPlayersAsList()) { + if (p.getColor() == logic.getGame().getActiveColor()) { + PowerCard cardToDraw = logic.getGame().draw(); + p.addHandCard(cardToDraw); + logic.getServerSender().send(logic.getGame().getPlayerIdByColor(p.getColor()), new DrawCardMessage(cardToDraw)); + } + else { + logic.getServerSender().send(logic.getGame().getPlayerIdByColor(p.getColor()), new DrawCardMessage(new HiddenCard())); + } + } } - logic.getServerSender().broadcast(new MoveMessage(movePiece, homeMove, targIdx)); this.choosePieceAutomaton.getTurnAutomaton().setCurrentState(this.choosePieceAutomaton.getTurnAutomaton().getMovePieceState()); } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/StartPieceState.java b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/StartPieceState.java index 9a9b7e6a..f7b30e06 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/StartPieceState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/choosepiece/StartPieceState.java @@ -4,6 +4,7 @@ import pp.mdga.game.Piece; import pp.mdga.game.Player; import pp.mdga.game.card.HiddenCard; +import pp.mdga.game.card.PowerCard; import pp.mdga.message.client.RequestMoveMessage; import pp.mdga.message.server.DrawCardMessage; import pp.mdga.message.server.MoveMessage; @@ -40,22 +41,12 @@ public void enter() { } @Override - public void received(RequestMoveMessage msg, int from){ + public void received(RequestMoveMessage msg, int from) { LOGGER.log(System.Logger.Level.INFO, "Received RequestMoveMessage message. is piece equals: " + piece.equals(msg.getPiece())); if (piece.equals(msg.getPiece())) { int targetIndex = calculateTargetIndex(piece); Node targetNode = logic.getGame().getBoard().getInfield()[targetIndex]; - if(targetNode.isBonus()) { - for (Player p : logic.getGame().getPlayersAsList()) { - if(p.getColor() == logic.getGame().getActiveColor()) { - logic.getServerSender().send(logic.getGame().getPlayerIdByColor(p.getColor()), new DrawCardMessage(logic.getGame().draw())); - } else { - logic.getServerSender().send(logic.getGame().getPlayerIdByColor(p.getColor()), new DrawCardMessage(new HiddenCard())); - } - } - } - //send MoveMessage logic.getServerSender().broadcast(new MoveMessage(piece, false, targetIndex)); @@ -63,13 +54,26 @@ public void received(RequestMoveMessage msg, int from){ logic.getGame().getBoard().getInfield()[logic.getGame().getBoard().getInfieldIndexOfPiece(piece)].clearOccupant(); Piece occ = targetNode.getOccupant(); - if (occ != null){ + if (occ != null) { //move occ to waiting logic.getGame().getPlayerByColor(occ.getColor()).addWaitingPiece(occ); } //move piece to targetNode targetNode.setOccupant(piece); + if (targetNode.isBonus()) { + for (Player p : logic.getGame().getPlayersAsList()) { + if (p.getColor() == logic.getGame().getActiveColor()) { + PowerCard cardToDraw = logic.getGame().draw(); + p.addHandCard(cardToDraw); + logic.getServerSender().send(logic.getGame().getPlayerIdByColor(p.getColor()), new DrawCardMessage(cardToDraw)); + } + else { + logic.getServerSender().send(logic.getGame().getPlayerIdByColor(p.getColor()), new DrawCardMessage(new HiddenCard())); + } + } + } + this.choosePieceAutomaton.getTurnAutomaton().setCurrentState(this.choosePieceAutomaton.getTurnAutomaton().getMovePieceState()); } } diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/powercard/ChoosePowerCardState.java b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/powercard/ChoosePowerCardState.java index 3958a338..577ebc2f 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/powercard/ChoosePowerCardState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/powercard/ChoosePowerCardState.java @@ -1,6 +1,8 @@ package pp.mdga.server.automaton.game.turn.powercard; +import pp.mdga.game.BonusCard; import pp.mdga.game.card.HiddenCard; +import pp.mdga.game.card.PowerCard; import pp.mdga.game.card.ShieldCard; import pp.mdga.game.card.SwapCard; import pp.mdga.game.card.TurboCard; @@ -12,6 +14,8 @@ import pp.mdga.server.automaton.game.turn.PowerCardState; import pp.mdga.visitor.Visitor; +import java.util.List; + public class ChoosePowerCardState extends PowerCardAutomatonState implements Visitor { private static final System.Logger LOGGER = System.getLogger(ChoosePowerCardState.class.getName()); @@ -44,7 +48,10 @@ public void exit() { @Override public void received(SelectCardMessage msg, int from) { - if (this.powerCardAutomaton.getVisitor().getCards().contains(msg.getCard())) { + BonusCard receivedCard = msg.getCard().getCard(); + List acceptedCards = powerCardAutomaton.getVisitor().getCards().stream().map(PowerCard::getCard).toList(); + + if (acceptedCards.contains(receivedCard)) { this.powerCardAutomaton.setSelectedCard(msg.getCard()); msg.getCard().accept(this); } else { diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/rolldice/FirstRollState.java b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/rolldice/FirstRollState.java index 09b518b0..9d101bb0 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/rolldice/FirstRollState.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/server/automaton/game/turn/rolldice/FirstRollState.java @@ -22,6 +22,7 @@ public class FirstRollState extends RollDiceAutomatonState { private static final System.Logger LOGGER = System.getLogger(FirstRollState.class.getName()); private List moveablePieces; private int roll; + private boolean isDied = false; /** * Constructs a server state of the specified game logic. @@ -37,6 +38,7 @@ public FirstRollState(RollDiceState rollDiceAutomaton, ServerGameLogic logic) { public void enter() { LOGGER.log(System.Logger.Level.INFO, "Entered FirstRollState state."); roll = 0; + isDied = false; moveablePieces = new ArrayList<>(); for (Piece piece : this.logic.getGame().getPlayerByColor(this.logic.getGame().getActiveColor()).getPieces()) { if (piece.getState() == PieceState.HOME || piece.getState() == PieceState.ACTIVE) { @@ -62,14 +64,16 @@ public void received(RequestDieMessage msg, int from) { roll = this.logic.getGame().getDie().shuffle(); this.logic.getGame().setDiceEyes(roll); this.logic.getServerSender().broadcast(new DieMessage(roll)); + isDied = true; } @Override public void received(AnimationEndMessage msg, int from) { if (from != this.logic.getGame().getActivePlayerId()) { - return; - } - if (!moveablePieces.isEmpty()) { + LOGGER.log(System.Logger.Level.INFO, "Received AnimationEndMessage from wrong player."); + } else if (!isDied){ + LOGGER.log(System.Logger.Level.INFO, "Received AnimationEndMessage without the active player rolling a die."); + } else if (!moveablePieces.isEmpty()) { this.logic.getServerSender().send(this.logic.getGame().getActivePlayerId(), new ChoosePieceStateMessage()); this.rollDiceAutomaton.getTurnAutomaton().setCurrentState(this.rollDiceAutomaton.getTurnAutomaton().getChoosePieceState()); } else { diff --git a/Projekte/mdga/model/src/main/java/pp/mdga/visitor/ServerCardVisitor.java b/Projekte/mdga/model/src/main/java/pp/mdga/visitor/ServerCardVisitor.java index 64efdc03..b4964fef 100644 --- a/Projekte/mdga/model/src/main/java/pp/mdga/visitor/ServerCardVisitor.java +++ b/Projekte/mdga/model/src/main/java/pp/mdga/visitor/ServerCardVisitor.java @@ -41,7 +41,13 @@ public ServerCardVisitor(ServerGameLogic logic) { */ @Override public void visit(TurboCard card) { - this.cards.add(card); + for (Piece piece : this.logic.getGame().getActivePlayer().getPieces()) { + if (piece.getState() == PieceState.ACTIVE) { + if (!this.cards.stream().map(PowerCard::getCard).toList().contains(card.getCard())) { + this.cards.add(card); + } + } + } } /** @@ -52,7 +58,7 @@ public void visit(TurboCard card) { @Override public void visit(SwapCard card) { List possibleOwnPieces = new ArrayList<>(); - for (Piece piece : this.logic.getGame().getPlayerByColor(this.logic.getGame().getActiveColor()).getPieces()) { + for (Piece piece : this.logic.getGame().getActivePlayer().getPieces()) { if (piece.getState() == PieceState.ACTIVE) { if (!possibleOwnPieces.contains(piece)) { possibleOwnPieces.add(piece); @@ -62,7 +68,7 @@ public void visit(SwapCard card) { List possibleOtherPieces = new ArrayList<>(); for (var player : this.logic.getGame().getPlayers().values()) { - if (player != this.logic.getGame().getPlayerByColor(this.logic.getGame().getActiveColor())) { + if (player != this.logic.getGame().getActivePlayer()) { for (Piece piece : player.getPieces()) { if (piece.getState() == PieceState.ACTIVE) { if (!possibleOtherPieces.contains(piece)) { @@ -76,7 +82,9 @@ public void visit(SwapCard card) { if (!possibleOtherPieces.isEmpty() && !possibleOwnPieces.isEmpty()) { this.swapOwnPieces.addAll(possibleOwnPieces); this.swapOtherPieces.addAll(possibleOtherPieces); - this.cards.add(card); + if (!this.cards.stream().map(PowerCard::getCard).toList().contains(card.getCard())) { + this.cards.add(card); + } } } @@ -92,7 +100,7 @@ public void visit(ShieldCard card) { if (!this.shieldPieces.contains(piece)) { this.shieldPieces.add(piece); } - if (!this.cards.contains(card)) { + if (!this.cards.stream().map(PowerCard::getCard).toList().contains(card.getCard())) { this.cards.add(card); } } diff --git a/Projekte/mdga/model/src/main/resources/mdga.properties b/Projekte/mdga/model/src/main/resources/mdga.properties index 0495f73c..2357a3b3 100644 --- a/Projekte/mdga/model/src/main/resources/mdga.properties +++ b/Projekte/mdga/model/src/main/resources/mdga.properties @@ -2,10 +2,10 @@ lobby.deny.join=The lobby is already full. server.shutdown=The server has shut down. incorrect.request.0=The selected TSK is already occupied. incorrect.request.1=No TSK is available for selection. -incorrect.request.2=Test -incorrect.request.3=Test -incorrect.request.4=Test -incorrect.request.5=Test +incorrect.request.2=Chosen PowerCard cannot be played. +incorrect.request.3=Selected to many or wrong pieces. +incorrect.request.4=Did not select exactly 2 pieces or selected wrong pieces. +incorrect.request.5=Cannot start game because not everyone is ready. diff --git a/Projekte/mdga/model/src/main/resources/mdga_de.properties b/Projekte/mdga/model/src/main/resources/mdga_de.properties index c2103b99..3410701a 100644 --- a/Projekte/mdga/model/src/main/resources/mdga_de.properties +++ b/Projekte/mdga/model/src/main/resources/mdga_de.properties @@ -2,7 +2,7 @@ lobby.deny.join=Die Lobby ist bereits voll. server.shutdown=Der Server wurde heruntergefahren. incorrect.request.0=Die ausgewählte TSK ist bereits belegt. incorrect.request.1=Es gibt keine freie TSK mehr, welche ausgewählt werden kann. -incorrect.request.2=Test -incorrect.request.3=Test -incorrect.request.4=Test -incorrect.request.5=Test +incorrect.request.2=Die ausgewälte Powerkarte kann nicht eingesetzt werden. +incorrect.request.3=Du hast zuviele, oder eine falsche Figur ausgewählt. +incorrect.request.4=Du hast nicht genau zwei Figuren, oder falsche Figuren ausgewählt. +incorrect.request.5=Du kannst das Spiel nicht starten, da nicht alle Spieler bereit sind.