merge development into test #26

Merged
j23f0712 merged 95 commits from development into dev/test 2024-12-01 21:02:48 +01:00
6 changed files with 261 additions and 20 deletions
Showing only changes of commit 9067a9b04c - Show all commits

View File

@@ -1,5 +1,10 @@
package pp.mdga.client; package pp.mdga.client;
/**
* Represents different assets in the application. Each asset may have an associated model path,
* diffuse texture path, and a size factor. The enum provides multiple constructors to handle
* varying levels of detail for different assets.
*/
public enum Asset { public enum Asset {
bigTent, bigTent,
cardStack, cardStack,
@@ -41,6 +46,9 @@ public enum Asset {
private final float size; private final float size;
private static final String root = "Models/"; private static final String root = "Models/";
/**
* Default constructor. Initializes modelPath and diffPath based on the enum name and sets default size to 1.0.
*/
Asset() { Asset() {
String folderFileName = "./" + root + name() + "/" + name(); String folderFileName = "./" + root + name() + "/" + name();
this.modelPath = folderFileName + ".j3o"; this.modelPath = folderFileName + ".j3o";
@@ -48,12 +56,23 @@ public enum Asset {
this.size = 1f; this.size = 1f;
} }
/**
* Constructor with specific model path and diffuse texture path.
*
* @param modelPath Path to the 3D model file.
* @param diffPath Path to the diffuse texture file.
*/
Asset(String modelPath, String diffPath) { Asset(String modelPath, String diffPath) {
this.modelPath = modelPath; this.modelPath = modelPath;
this.diffPath = diffPath; this.diffPath = diffPath;
this.size = 1f; this.size = 1f;
} }
/**
* Constructor with specific model path. Diffuse texture path is derived based on enum name.
*
* @param modelPath Path to the 3D model file.
*/
Asset(String modelPath) { Asset(String modelPath) {
String folderFileName = "./" + root + name() + "/" + name(); String folderFileName = "./" + root + name() + "/" + name();
this.modelPath = modelPath; this.modelPath = modelPath;
@@ -61,6 +80,11 @@ public enum Asset {
this.size = 1f; this.size = 1f;
} }
/**
* Constructor with specific size. Model and texture paths are derived based on enum name.
*
* @param size Scaling factor for the asset.
*/
Asset(float size) { Asset(float size) {
String folderFileName = "./" + root + name() + "/" + name(); String folderFileName = "./" + root + name() + "/" + name();
this.modelPath = folderFileName + ".j3o"; this.modelPath = folderFileName + ".j3o";
@@ -68,20 +92,42 @@ public enum Asset {
this.size = size; this.size = size;
} }
/**
* Constructor with specific model path, diffuse texture path, and size.
*
* @param modelPath Path to the 3D model file.
* @param diffPath Path to the diffuse texture file.
* @param size Scaling factor for the asset.
*/
Asset(String modelPath, String diffPath, float size){ Asset(String modelPath, String diffPath, float size){
this.modelPath = modelPath; this.modelPath = modelPath;
this.diffPath = diffPath; this.diffPath = diffPath;
this.size = size; this.size = size;
} }
/**
* Gets the model path for the asset.
*
* @return Path to the 3D model file.
*/
public String getModelPath() { public String getModelPath() {
return modelPath; return modelPath;
} }
/**
* Gets the diffuse texture path for the asset.
*
* @return Path to the diffuse texture file, or null if not applicable.
*/
public String getDiffPath() { public String getDiffPath() {
return diffPath; return diffPath;
} }
/**
* Gets the scaling factor for the asset.
*
* @return The size of the asset.
*/
public float getSize() { public float getSize() {
return size; return size;
} }

View File

@@ -32,6 +32,12 @@ public class InputSynchronizer {
private CardControl hoverCard; private CardControl hoverCard;
private PieceControl hoverPiece; private PieceControl hoverPiece;
/**
* Constructor initializes the InputSynchronizer with the application context.
* Sets up input mappings and listeners for user interactions.
*
* @param app The application instance
*/
InputSynchronizer(MdgaApp app) { InputSynchronizer(MdgaApp app) {
this.app = app; this.app = app;
@@ -41,6 +47,9 @@ public class InputSynchronizer {
setupInput(); setupInput();
} }
/**
* Configures input mappings for various actions and binds them to listeners.
*/
private void setupInput() { private void setupInput() {
inputManager.addMapping("Settings", new KeyTrigger(KeyInput.KEY_ESCAPE)); inputManager.addMapping("Settings", new KeyTrigger(KeyInput.KEY_ESCAPE));
inputManager.addMapping("Forward", new KeyTrigger(KeyInput.KEY_RETURN)); inputManager.addMapping("Forward", new KeyTrigger(KeyInput.KEY_RETURN));
@@ -61,6 +70,9 @@ private void setupInput() {
private boolean test = false; private boolean test = false;
/**
* Handles action-based input events such as key presses and mouse clicks.
*/
private final ActionListener actionListener = new ActionListener() { private final ActionListener actionListener = new ActionListener() {
@Override @Override
public void onAction(String name, boolean isPressed, float tpf) { public void onAction(String name, boolean isPressed, float tpf) {
@@ -105,6 +117,9 @@ else if(boardSelect != null) {
} }
}; };
/**
* Handles analog-based input events such as mouse movement and scrolling.
*/
private final AnalogListener analogListener = new AnalogListener() { private final AnalogListener analogListener = new AnalogListener() {
@Override @Override
public void onAnalog(String name, float value, float tpf) { public void onAnalog(String name, float value, float tpf) {
@@ -127,6 +142,9 @@ else if (name.equals("MouseLeft") || name.equals("MouseRight") || name.equals("M
} }
}; };
/**
* Detects the hovered piece and updates its hover state.
*/
private <T extends AbstractControl> T checkHover(Camera cam, Node root, Class<T> controlType) { private <T extends AbstractControl> T checkHover(Camera cam, Node root, Class<T> controlType) {
CollisionResults results = new CollisionResults(); CollisionResults results = new CollisionResults();
Ray ray = new Ray(cam.getLocation(), getMousePos(cam).subtract(cam.getLocation()).normalize()); Ray ray = new Ray(cam.getLocation(), getMousePos(cam).subtract(cam.getLocation()).normalize());
@@ -137,6 +155,9 @@ private <T extends AbstractControl> T checkHover(Camera cam, Node root, Class<T>
return null; return null;
} }
/**
* Detects the hovered card and updates its hover state.
*/
private <T extends AbstractControl> T checkHoverOrtho(Camera cam, Node root, Class<T> controlType) { private <T extends AbstractControl> T checkHoverOrtho(Camera cam, Node root, Class<T> controlType) {
CollisionResults results = new CollisionResults(); CollisionResults results = new CollisionResults();
Vector3f mousePos = getMousePos(cam); Vector3f mousePos = getMousePos(cam);
@@ -152,63 +173,110 @@ private <T extends AbstractControl> T checkHoverOrtho(Camera cam, Node root, Cla
return null; return null;
} }
/**
* Handles the hover state for a piece in the game.
* Checks if a piece is being hovered over, updates the hover state, and triggers hover effects.
*/
private void hoverPiece() { private void hoverPiece() {
if (app.getView() instanceof GameView gameView) { if (app.getView() instanceof GameView gameView) {
PieceControl control = checkPiece(); PieceControl control = checkPiece();
if (control != null) { if (control != null) {
if(control != hoverPiece){ if (control != hoverPiece) {
pieceOff(); pieceOff();
hoverPiece = control; hoverPiece = control;
hoverPiece.hover(); hoverPiece.hover();
} }
} else {
pieceOff();
} }
else pieceOff();
} }
} }
/**
* Handles the hover state for a card in the game.
* Checks if a card is being hovered over, updates the hover state, and triggers hover effects.
*/
private void hoverCard() { private void hoverCard() {
if (app.getView() instanceof GameView gameView) { if (app.getView() instanceof GameView gameView) {
CardControl control = checkCard(gameView); CardControl control = checkCard(gameView);
if (control != null) { if (control != null) {
if(control != hoverCard){ if (control != hoverCard) {
cardOff(); cardOff();
hoverCard = control; hoverCard = control;
hoverCard.hover(); hoverCard.hover();
} }
} else {
cardOff();
} }
else cardOff();
} }
} }
private PieceControl checkPiece(){ /**
* Checks if a piece is being hovered over in the 3D game world.
*
* @return The PieceControl of the hovered piece, or null if no piece is hovered.
*/
private PieceControl checkPiece() {
return checkHover(app.getCamera(), app.getRootNode(), PieceControl.class); return checkHover(app.getCamera(), app.getRootNode(), PieceControl.class);
} }
private CardControl checkCard(GameView gameView){ /**
return checkHoverOrtho(gameView.getGuiHandler().getCardLayerCamera(), gameView.getGuiHandler().getCardLayerRootNode(), CardControl.class); * Checks if a card is being hovered over in the 2D card layer.
*
* @param gameView The current game view.
* @return The CardControl of the hovered card, or null if no card is hovered.
*/
private CardControl checkCard(GameView gameView) {
return checkHoverOrtho(
gameView.getGuiHandler().getCardLayerCamera(),
gameView.getGuiHandler().getCardLayerRootNode(),
CardControl.class
);
} }
private void pieceOff(){ /**
if(hoverPiece != null) hoverPiece.hoverOff(); * Disables the hover effect on the currently hovered piece, if any.
*/
private void pieceOff() {
if (hoverPiece != null) hoverPiece.hoverOff();
hoverPiece = null; hoverPiece = null;
} }
private void cardOff(){ /**
if(hoverCard != null) hoverCard.hoverOff(); * Disables the hover effect on the currently hovered card, if any.
*/
private void cardOff() {
if (hoverCard != null) hoverCard.hoverOff();
hoverCard = null; hoverCard = null;
} }
private Vector3f getMousePos(Camera cam){ /**
* Retrieves the current mouse position in the 3D world using the specified camera.
*
* @param cam The camera used for determining the mouse position.
* @return A Vector3f representing the mouse position in the 3D world.
*/
private Vector3f getMousePos(Camera cam) {
Vector2f mousePositionScreen = inputManager.getCursorPosition(); Vector2f mousePositionScreen = inputManager.getCursorPosition();
Vector3f world = cam.getWorldCoordinates(mousePositionScreen, 0); Vector3f world = cam.getWorldCoordinates(mousePositionScreen, 0);
if (cam.isParallelProjection()) world.setZ(0); if (cam.isParallelProjection()) world.setZ(0);
return world; return world;
} }
/**
* Gets the current rotation angle of the game element.
*
* @return The rotation angle in degrees, normalized to 360 degrees.
*/
public float getRotation() { public float getRotation() {
return (rotationAngle / 2) % 360; return (rotationAngle / 2) % 360;
} }
/**
* Gets the current scroll value.
*
* @return The scroll value as an integer.
*/
public int getScroll() { public int getScroll() {
return scrollValue; return scrollValue;
} }

View File

@@ -7,23 +7,54 @@
import com.jme3.system.AppSettings; import com.jme3.system.AppSettings;
import pp.mdga.client.view.*; import pp.mdga.client.view.*;
/**
* Main application class for the MdgaApp game.
* This class extends {@link SimpleApplication} and manages the game's lifecycle, states, and main components.
*/
public class MdgaApp extends SimpleApplication { public class MdgaApp extends SimpleApplication {
/** Handles animations in the application. */
private AnimationHandler animationHandler; private AnimationHandler animationHandler;
/** Handles acoustic effects and state-based sounds. */
private AcousticHandler acousticHandler; private AcousticHandler acousticHandler;
/** Synchronizes notifications throughout the application. */
private NotificationSynchronizer notificationSynchronizer; private NotificationSynchronizer notificationSynchronizer;
/** Manages input events and synchronization. */
private InputSynchronizer inputSynchronizer; private InputSynchronizer inputSynchronizer;
/** Synchronizes game models. */
private ModelSynchronizer modelSynchronizer; private ModelSynchronizer modelSynchronizer;
MdgaView view = null; /** The currently active view in the application. */
private MdgaView view = null;
/** The current state of the application. */
private MdgaState state = null; private MdgaState state = null;
private static float imageScale = 1.5f; /** Scale for rendering images. */
private static final float imageScale = 1.5f;
/** The main menu view. */
private MdgaView mainView; private MdgaView mainView;
/** The lobby view. */
private MdgaView lobbyView; private MdgaView lobbyView;
/** The game view. */
private MdgaView gameView; private MdgaView gameView;
/** The ceremony view. */
private MdgaView ceremonyView; private MdgaView ceremonyView;
/**
* Main entry point for the application.
* Configures settings and starts the application.
*
* @param args command-line arguments (not used)
*/
public static void main(String[] args) { public static void main(String[] args) {
AppSettings settings = new AppSettings(true); AppSettings settings = new AppSettings(true);
settings.setSamples(128); settings.setSamples(128);
@@ -38,6 +69,9 @@ public static void main(String[] args) {
app.start(); app.start();
} }
/**
* Initializes the application by setting up handlers, views, and entering the default state.
*/
@Override @Override
public void simpleInitApp() { public void simpleInitApp() {
GuiGlobals.initialize(this); GuiGlobals.initialize(this);
@@ -60,6 +94,11 @@ public void simpleInitApp() {
enter(MdgaState.MAIN); enter(MdgaState.MAIN);
} }
/**
* Updates the application on each frame. Updates the view, acoustic handler, and notifications.
*
* @param tpf time per frame, used for smooth updating
*/
@Override @Override
public void simpleUpdate(float tpf) { public void simpleUpdate(float tpf) {
view.update(tpf); view.update(tpf);
@@ -67,8 +106,14 @@ public void simpleUpdate(float tpf) {
notificationSynchronizer.update(); notificationSynchronizer.update();
} }
/**
* Transitions the application to a new state.
*
* @param state the new state to enter
* @throws RuntimeException if attempting to enter the {@link MdgaState#NONE} state
*/
public void enter(MdgaState state) { public void enter(MdgaState state) {
if(null != view) { if (null != view) {
view.leave(); view.leave();
} }
@@ -88,7 +133,7 @@ public void enter(MdgaState state) {
view = ceremonyView; view = ceremonyView;
break; break;
case NONE: case NONE:
throw new RuntimeException("cant enter state NONE"); throw new RuntimeException("Cannot enter state NONE");
} }
acousticHandler.playState(state); acousticHandler.playState(state);
@@ -96,29 +141,83 @@ public void enter(MdgaState state) {
view.enter(); view.enter();
} }
/**
* Gets the animation handler.
*
* @return the {@link AnimationHandler} instance
*/
public AnimationHandler getAnimationHandler() { public AnimationHandler getAnimationHandler() {
return animationHandler; return animationHandler;
} }
/**
* Gets the acoustic handler.
*
* @return the {@link AcousticHandler} instance
*/
public AcousticHandler getAcousticHandler() { public AcousticHandler getAcousticHandler() {
return acousticHandler; return acousticHandler;
} }
public MdgaState getState() {return state; } /**
* Gets the current state of the application.
*
* @return the current {@link MdgaState}
*/
public MdgaState getState() {
return state;
}
/**
* Gets the image scaling factor.
*
* @return the image scale as a float
*/
public float getImageScale() { public float getImageScale() {
return imageScale; return imageScale;
} }
/**
* Gets the currently active view.
*
* @return the active {@link MdgaView}
*/
public MdgaView getView() { public MdgaView getView() {
return view; return view;
} }
/**
* Gets the model synchronizer.
*
* @return the {@link ModelSynchronizer} instance
*/
public ModelSynchronizer getModelSynchronize() { public ModelSynchronizer getModelSynchronize() {
return modelSynchronizer; return modelSynchronizer;
} }
public InputSynchronizer getInputSynchronize() { return inputSynchronizer; } /**
* Gets the input synchronizer.
*
* @return the {@link InputSynchronizer} instance
*/
public InputSynchronizer getInputSynchronize() {
return inputSynchronizer;
}
public NotificationSynchronizer getNotificationSynchronizer() { return notificationSynchronizer; } /**
* Gets the notification synchronizer.
*
* @return the {@link NotificationSynchronizer} instance
*/
public NotificationSynchronizer getNotificationSynchronizer() {
return notificationSynchronizer;
}
/**
* Prepares the app for a new game cycle.
*/
public void setup() {
}
} }

View File

@@ -1,9 +1,35 @@
package pp.mdga.client; package pp.mdga.client;
/**
* Enum representing the various states of the MdgaApp application.
* Each state corresponds to a distinct phase or mode of the application.
*/
public enum MdgaState { public enum MdgaState {
/**
* Represents an undefined or uninitialized state.
* This state should not be entered during normal application execution.
*/
NONE, NONE,
/**
* Represents the main menu state.
* This is typically the first state entered when the application starts.
*/
MAIN, MAIN,
/**
* Represents the lobby state where players can prepare or wait before starting a game.
*/
LOBBY, LOBBY,
/**
* Represents the main gameplay state where the core game mechanics take place.
*/
GAME, GAME,
/**
* Represents the ceremony state, typically used for post-game events or celebrations.
*/
CEREMONY; CEREMONY;
} }

View File

@@ -117,7 +117,7 @@ private void handleGame(Notification notification) {
boardHandler.moveHomePiece(home.getPieceId(), home.getHomeIndex()); boardHandler.moveHomePiece(home.getPieceId(), home.getHomeIndex());
guiHandler.hideText(); guiHandler.hideText();
} else if (notification instanceof InterruptNotification) { } else if (notification instanceof InterruptNotification) {
//TODO ??? app.enter(MdgaState.LOBBY);
} else if (notification instanceof MovePieceNotification n) { } else if (notification instanceof MovePieceNotification n) {
if(n.isMoveStart()) { if(n.isMoveStart()) {
//StartMove //StartMove

View File

@@ -34,6 +34,8 @@ public MainView(MdgaApp app) {
@Override @Override
public void onEnter() { public void onEnter() {
app.setup();
guiNode.attachChild(background); guiNode.attachChild(background);
enterSub(SubState.MAIN); enterSub(SubState.MAIN);