Coverage Summary for Class: GUISocketListener (it.polimi.ingsw.Client.GUI.Listeners)
| Class | Class, % | Method, % | Branch, % | Line, % |
|---|---|---|---|---|
| GUISocketListener | 0% (0/1) | 0% (0/5) | 0% (0/18) | 0% (0/43) |
1 package it.polimi.ingsw.Client.GUI.Listeners; 2 3 import it.polimi.ingsw.Client.GUI.Context; 4 import it.polimi.ingsw.Client.GUI.Panels.GameInProgressPanel; 5 import it.polimi.ingsw.Client.GUI.Panels.StartPanel; 6 import it.polimi.ingsw.Controller.Actions.EndTurnOfActionPhase; 7 import it.polimi.ingsw.Controller.Actions.PlayerAction; 8 import it.polimi.ingsw.Misc.Pair; 9 import it.polimi.ingsw.Network.SocketWrapper; 10 import it.polimi.ingsw.Server.Messages.Message; 11 import it.polimi.ingsw.Server.Messages.ServerResponses.*; 12 import it.polimi.ingsw.Server.Messages.ServerResponses.SupportStructures.StatusCode; 13 14 import javax.swing.*; 15 import java.io.IOException; 16 import java.util.ArrayList; 17 import java.util.List; 18 19 /** 20 * Handles messages received from server and keep a record of current player's actions executed during its turn 21 */ 22 public class GUISocketListener implements Runnable { 23 /** 24 * List of actions executed by current player and their feedbacks 25 */ 26 private final List<Pair<PlayerAction, PlayerActionFeedback>> requestAndFeedback = new ArrayList<>(); 27 /** 28 * Context received from GameInProgressPanel 29 */ 30 private final Context ctx; 31 /** 32 * SocketWrapper used to communicate with Server 33 */ 34 private final SocketWrapper sw; 35 /** 36 * JTabbedPane containing all others JPanels 37 */ 38 private GameInProgressPanel gameInProgressPanel; 39 /** 40 * Last player's request sent to Server 41 */ 42 private PlayerAction playerActionRequest; 43 44 45 /** 46 * Create a new GUIReader 47 * 48 * @param ctx Context containing socket and GUI's window 49 */ 50 public GUISocketListener(Context ctx) { 51 this.gameInProgressPanel = null; 52 this.playerActionRequest = null; 53 this.sw = ctx.getSocketWrapper(); 54 this.ctx = ctx; 55 } 56 57 /** 58 * Listen for Server's responses and updated window basing on responses 59 */ 60 @Override 61 public void run() { 62 while (true) { 63 try { 64 //wait server's response 65 Message input = sw.awaitMessage(); 66 switch (input) { 67 case LobbyClosed ignored -> { 68 JOptionPane.showMessageDialog(null, "Lobby was closed by the server.\n" + 69 "Client is disconnecting from the server.", "Lobby closed", JOptionPane.INFORMATION_MESSAGE); 70 //close socket and return to StartPanel 71 sw.close(); 72 ctx.getWindow().changeView(new StartPanel(ctx)); 73 return; 74 } 75 case ClientDisconnected clientDisconnected -> 76 JOptionPane.showMessageDialog(null, "Client " + clientDisconnected.getLastDisconnectedNickname() + 77 " just disconnected.", "Client disconnected", JOptionPane.INFORMATION_MESSAGE); 78 case ModelUpdated modelUpdated -> { 79 //create a new GameInProgressPanel with updated model 80 this.gameInProgressPanel = new GameInProgressPanel(ctx, modelUpdated.getModel(), this, gameInProgressPanel); 81 ctx.getWindow().changeView(this.gameInProgressPanel); 82 return; 83 } 84 case PlayerActionFeedback playerActionFeedback -> { 85 //create a new Pair with saved player's request and feedback received 86 requestAndFeedback.add(new Pair<>(this.playerActionRequest, playerActionFeedback)); 87 //show eventual fail report 88 if (playerActionFeedback.getStatusCode() == StatusCode.Fail) 89 JOptionPane.showMessageDialog(null, playerActionFeedback.getReport()); 90 //clear history when endTurn action has been performed by user 91 if (playerActionRequest.getClass().equals(EndTurnOfActionPhase.class) && playerActionFeedback.getStatusCode() == StatusCode.Success) { 92 requestAndFeedback.clear(); 93 } 94 playerActionRequest = null; 95 } 96 case GameOver ignored -> { 97 return; 98 } 99 case InvalidRequest ignored -> 100 JOptionPane.showMessageDialog(null, "Your request has not been executed, probably you are trying to play out of turn", 101 "Warning", JOptionPane.INFORMATION_MESSAGE); 102 default -> throw new IllegalStateException("Unexpected value: " + input.getClass()); 103 } 104 } catch (Exception e) { 105 JOptionPane.showMessageDialog(null, "Error in the connection with the server", "Error", JOptionPane.INFORMATION_MESSAGE); 106 try { 107 sw.close(); 108 } catch (IOException ex) { 109 throw new RuntimeException(ex); 110 } 111 ctx.getWindow().changeView(new StartPanel(ctx)); 112 return; 113 } 114 } 115 } 116 117 /** 118 * Save user's request that will be added in history after receiving its feedback 119 * 120 * @param playerActionRequest playerActionRequest to save 121 */ 122 public void savePlayerActionRequest(PlayerAction playerActionRequest) { 123 if (this.playerActionRequest == null) { 124 this.playerActionRequest = playerActionRequest; 125 } 126 } 127 128 /** 129 * Check to see if a new {@link it.polimi.ingsw.Server.Messages.Events.Requests.PlayerActionRequest} can be sent to the server 130 * or if the gui should wait before allowing any more actions to be sent 131 * 132 * @return true if the listener is polling for a feedback to a previous player's action, false otherwise 133 */ 134 public boolean awaitingPlayerActionFeedback() { 135 return playerActionRequest != null; 136 } 137 138 /** 139 * Count PlayerActions that have received a successful response from Server 140 * 141 * @param playerActionClass PlayerAction's class that will be counted 142 * @return PlayerAction amount that received a successful response from Server 143 */ 144 public int getSuccessfulRequestsByType(Class<?> playerActionClass) { 145 List<PlayerActionFeedback> actions = requestAndFeedback.stream(). 146 filter(pair -> pair.first().getClass().equals(playerActionClass)).map(Pair::second).toList(); 147 148 return (int) actions.stream().filter(playerActionFeedback -> playerActionFeedback.getStatusCode() == StatusCode.Success).count(); 149 } 150 }