diff --git a/Projekte/.run/MdgaApp.run.xml b/Projekte/.run/MdgaApp.run.xml index a33a2cd3..051df2ea 100644 --- a/Projekte/.run/MdgaApp.run.xml +++ b/Projekte/.run/MdgaApp.run.xml @@ -1,18 +1,17 @@ - - diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/AcousticHandler.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/AcousticHandler.java new file mode 100644 index 00000000..8ae659df --- /dev/null +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/AcousticHandler.java @@ -0,0 +1,291 @@ +package pp.mdga.client.Acoustic; + +import com.jme3.system.NanoTimer; +import pp.mdga.client.MdgaApp; +import pp.mdga.client.MdgaState; + +import java.util.*; + +public class AcousticHandler { + private MdgaApp app; + + private MdgaState state = MdgaState.NONE; + + private boolean playGame = false; + private ArrayList gameTracks = new ArrayList<>(); + private NanoTimer trackTimer = new NanoTimer(); + + private boolean fading = false; + private NanoTimer fadeTimer = new NanoTimer(); + private static final float FADE_DURATION = 3.0f; + private static final float CROSSFADE_DURATION = 1.5f; + + private float mainVolume = 1.0f; + private float musicVolume = 1.0f; + private float soundVolume = 1.0f; + + private GameMusic scheduled = null; + private GameMusic playing = null; + private ArrayList sounds = new ArrayList<>(); + + public AcousticHandler(MdgaApp app) { + this.app = app; + } + + /** + * This method updates the acousticHandler and should be called every frame + */ + public void update() { + updateVolumeAndTrack(); + + if (playGame) { + updateGameTracks(); + } + + Iterator iterator = sounds.iterator(); + while (iterator.hasNext()) { + GameSound s = iterator.next(); + + s.update(getSoundVolumeTotal()); + + if (!s.isPlaying()) { + iterator.remove(); + } + } + } + + /** + * This method instantly plays a sound + * + * @param sound the sound to be played + */ + public void playSound(MdgaSound sound) { + ArrayList assets = new ArrayList(); + switch (sound) { + case LOST: + assets.add(new SoundAssetDelayVolume(SoundAsset.LOST, 1.0f, 0.0f)); + break; + case VICTORY: + assets.add(new SoundAssetDelayVolume(SoundAsset.VICTORY, 1.0f, 2.0f)); + break; + default: + + break; + } + + for (SoundAssetDelayVolume sawd : assets) { + GameSound gameSound = new GameSound(app, sawd.asset(), getSoundVolumeTotal(), sawd.subVolume(), sawd.delay()); + sounds.add(gameSound); + } + } + + /** + * This method fades the played music to fit the state. + * + * @param state the state of which the corresponding music should be played to be played + */ + public void playState(MdgaState state) { + if (this.state == state) { + return; + } + + MusicAsset asset = null; + + switch (state) { + case MAIN: + playGame = false; + asset = MusicAsset.MAIN_MENU; + break; + case LOBBY: + playGame = false; + asset = MusicAsset.LOBBY; + break; + case GAME: + addGameTracks(); + playGame = true; + assert (gameTracks.size() > 0) : "no more game music available"; + asset = gameTracks.remove(0); + break; + case CEREMONY: + playGame = false; + asset = MusicAsset.CEREMONY; + break; + } + + assert (null != asset) : "music sceduling went wrong"; + + scheduled = new GameMusic(app, asset, getMusicVolumeTotal(), asset.getSubVolume(), asset.getLoop()); + } + + /** + * Performs linear interpolation between two float values. + * + * @param start The starting value. + * @param end The ending value. + * @param t The interpolation factor, typically between 0 and 1. + * @return The interpolated value between start and end. + */ + private float lerp(float start, float end, float t) { + return start + t * (end - start); + } + + /** + * Updates the current volume and handles track crossfading logic. + * This method is responsible for fading out the currently playing track, + * fading in the scheduled track, and handling crossfade between the two tracks. + */ + private void updateVolumeAndTrack() { + if (playing == null && scheduled != null && !fading) { + playing = scheduled; + scheduled = null; + playing.play(); + return; + } + + if (scheduled != null && !fading) { + fading = true; + fadeTimer.reset(); + } + + if (fading) { + float time = fadeTimer.getTimeInSeconds(); + + if (time <= FADE_DURATION) { + float t = Math.min(time / FADE_DURATION, 1.0f); + float oldVolume = lerp(1.0f, 0.0f, t); + if (playing != null) { + playing.update(getMusicVolumeTotal() * oldVolume); + } + } + + if (time > FADE_DURATION && time <= FADE_DURATION + CROSSFADE_DURATION) { + float t = Math.min((time - FADE_DURATION) / CROSSFADE_DURATION, 1.0f); + float newVolume = lerp(0.0f, 1.0f, t); + + if (!scheduled.isPlaying()) { + scheduled.play(); + } + scheduled.update(getMusicVolumeTotal() * newVolume); + } + + if (time > FADE_DURATION + CROSSFADE_DURATION) { + if (playing != null) { + playing.pause(); + } + playing = scheduled; + scheduled = null; + + fading = false; + } + } + else if (playing != null) { + playing.update(getMusicVolumeTotal()); + } + } + + /** + * Adds a list of game tracks to the gameTracks collection and shuffles them. + * This method adds predefined game tracks to the track list and shuffles the order. + */ + private void addGameTracks() { + Random random = new Random(); + + for (int i = 1; i <= 6; i++) { + gameTracks.add(MusicAsset.valueOf("GAME_" + i)); + } + Collections.shuffle(gameTracks, random); + } + + /** + * Updates the current game tracks. If the currently playing track is nearing its end, + * a new track will be scheduled to play. If the list of game tracks is empty, it will be refreshed. + */ + private void updateGameTracks() { + if (playing.nearEnd(10)) { + if (gameTracks.isEmpty()) { + addGameTracks(); + } + } + + if (playing != null && playing.nearEnd(3) && trackTimer.getTimeInSeconds() > 20) { + trackTimer.reset(); + + MusicAsset nextTrack = gameTracks.remove(0); + + scheduled = new GameMusic(app, nextTrack, getMusicVolumeTotal(), nextTrack.getSubVolume(), nextTrack.getLoop()); + } + } + + /** + * Retrieves the main volume level. + * + * @return The current main volume level. + */ + public float getMainVolume() { + return mainVolume; + } + + /** + * Retrieves the music volume level. + * + * @return The current music volume level. + */ + public float getMusicVolume() { + return musicVolume; + } + + /** + * Retrieves the sound volume level. + * + * @return The current sound volume level. + */ + public float getSoundVolume() { + return soundVolume; + } + + /** + * Sets the main volume level. + * + * @param mainVolume The desired main volume level. + */ + public void setMainVolume(float mainVolume) { + this.mainVolume = mainVolume; + } + + /** + * Sets the music volume level. + * + * @param musicVolume The desired music volume level. + */ + public void setMusicVolume(float musicVolume) { + this.musicVolume = musicVolume; + } + + /** + * Sets the sound volume level. + * + * @param soundVolume The desired sound volume level. + */ + public void setSoundVolume(float soundVolume) { + this.soundVolume = soundVolume; + } + + /** + * Calculates the total music volume by multiplying the music volume by the main volume. + * + * @return The total music volume. + */ + float getMusicVolumeTotal() { + + return getMusicVolume() * getMainVolume(); + } + + /** + * Calculates the total sound volume by multiplying the sound volume by the main volume. + * + * @return The total sound volume. + */ + float getSoundVolumeTotal() { + return getSoundVolume() * getMainVolume(); + } +} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/GameMusic.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/GameMusic.java new file mode 100644 index 00000000..244f2b4e --- /dev/null +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/GameMusic.java @@ -0,0 +1,110 @@ +package pp.mdga.client.Acoustic; + +import com.jme3.audio.AudioData; +import com.jme3.audio.AudioNode; +import com.jme3.audio.AudioSource; +import pp.mdga.client.MdgaApp; + +/** + * Represents a game music track, including its playback controls and volume settings. + * This class manages the playback of a music track, allowing for playing, pausing, + * volume adjustment, and tracking the current status of the music. + */ +class GameMusic { + private float volume; + private final float subVolume; + private final AudioNode music; + + /** + * Constructs a new GameMusic object. + * + * @param app The instance of the application, used to access the asset manager. + * @param asset The music asset to be played. + * @param volume The total volume of the music, adjusted by the main volume. + * @param subVolume A relative volume that modifies the base music volume, typically a percentage. + * @param loop A flag indicating whether the music should loop once it finishes. + */ + GameMusic(MdgaApp app, MusicAsset asset, float volume, float subVolume, boolean loop) { + this.volume = volume; + this.subVolume = subVolume; + + music = new AudioNode(app.getAssetManager(), asset.getPath(), AudioData.DataType.Stream); + music.setPositional(false); + music.setDirectional(false); + music.setVolume(volume * subVolume); + + music.setLooping(loop); + } + + /** + * Plays the current music track. + * If the music is already initialized, it starts playback. + * If the music is not available, no action is performed. + */ + void play() { + if (null == music) { + return; + } + + music.play(); + } + + /** + * Pauses the current music track. + * If the music is not available or is not playing, no action is performed. + */ + void pause() { + if (null == music) { + return; + } + + music.stop(); + } + + /** + * Checks if the current music track is playing. + * + * @return true if the music is playing, false otherwise. + */ + boolean isPlaying() { + + return music.getStatus() == AudioSource.Status.Playing; + } + + /** + * Checks if the current music track is near the end. + * + * @param thresholdSeconds The threshold in seconds. If the remaining time is less than or equal to this value, + * the track is considered near the end. + * @return true if the track is near its end (within the threshold), false otherwise. + */ + boolean nearEnd(float thresholdSeconds) { + if (music == null || !isPlaying()) { + return false; + } + + float currentTime = music.getPlaybackTime(); // Current playback time in seconds + float duration = music.getAudioData().getDuration(); // Total duration in seconds + + if (duration <= 0) { + return false; + } + + float remainingTime = duration - currentTime; + + return remainingTime <= thresholdSeconds; + } + + /** + * Updates the volume of the music. + * If the volume has changed, it will adjust the music's volume accordingly. + * + * @param newVolume The new total volume for the music. + */ + void update(float newVolume) { + if (volume != newVolume) { + volume = newVolume; + music.setVolume(volume * subVolume); + } + } +} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/GameSound.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/GameSound.java new file mode 100644 index 00000000..6bc76b8b --- /dev/null +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/GameSound.java @@ -0,0 +1,83 @@ +package pp.mdga.client.Acoustic; + +import com.jme3.audio.AudioData; +import com.jme3.audio.AudioNode; +import com.jme3.audio.AudioSource; +import com.jme3.system.NanoTimer; +import pp.mdga.client.MdgaApp; + +/** + * Represents a game sound effect, with control over playback, volume, and timing. + * This class manages the playback of a sound effect, including starting playback after a delay, + * adjusting volume, and tracking whether the sound has finished playing. + */ +class GameSound { + private float volume; + final private float subVolume; + + private final AudioNode sound; + + private boolean playing = false; + private boolean finished = false; + + private float delay = 0.0f; + private NanoTimer timer = null; + + /** + * Constructs a new GameSound object. + * + * @param app The instance of the application, used to access the asset manager. + * @param asset The sound asset to be played. + * @param volume The total volume of the sound, adjusted by the main volume. + * @param subVolume A relative volume that modifies the base sound volume, typically a percentage. + * @param delay The delay before the sound starts playing, in seconds. + */ + GameSound(MdgaApp app, SoundAsset asset, float volume, float subVolume, float delay) { + this.volume = volume; + this.subVolume = subVolume; + this.delay = delay; + + sound = new AudioNode(app.getAssetManager(), asset.getPath(), AudioData.DataType.Buffer); + sound.setPositional(false); + sound.setDirectional(false); + sound.setLooping(false); + sound.setVolume(volume * subVolume); + + timer = new NanoTimer(); + } + + /** + * Checks if the sound is currently playing. + * + * @return true if the sound is playing, false otherwise. + */ + boolean isPlaying() { + return !finished; + } + + /** + * Updates the sound playback, adjusting the volume if necessary, and starting + * the sound after the specified delay. + * + * @param newVolume The new total volume for the sound. + */ + void update(float newVolume) { + if (!playing && timer.getTimeInSeconds() > delay) { + sound.play(); + playing = true; + } + + if (!playing) { + return; + } + + if (volume != newVolume) { + volume = newVolume; + sound.setVolume(volume * subVolume); + } + + if (sound != null && sound.getStatus() == AudioSource.Status.Playing) { + finished = true; + } + } +} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/MdgaSound.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/MdgaSound.java new file mode 100644 index 00000000..b70d25c2 --- /dev/null +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/MdgaSound.java @@ -0,0 +1,23 @@ +package pp.mdga.client.Acoustic; + +/** + * Enum representing the various sound effects used in the game. + * Each sound corresponds to an event or action in the game and may consist of one or more + * audio files, potentially with time delays between them. + *

+ * These sounds are used to play specific audio cues, such as when a dice is rolled, + * a turn starts or ends, a piece is moved or lost, and various other events in the game. + */ +public enum MdgaSound { + DICE_ROLL, + TURN_START, + TURN_END, + PIECE_END, + PIECE_MOVE, + PIECE_LOST, + SELECT, + DESELECT, + HURRY, + VICTORY, + LOST +} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/MusicAsset.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/MusicAsset.java new file mode 100644 index 00000000..691fbe70 --- /dev/null +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/MusicAsset.java @@ -0,0 +1,76 @@ +package pp.mdga.client.Acoustic; + +/** + * Enum representing various music assets used in the game. + * Each constant corresponds to a specific music track, along with its properties such as file path, + * looping behavior, and relative volume (subVolume). + * These music assets are used to control the music that plays in different parts of the game, such as menus and in-game music. + */ +enum MusicAsset { + MAIN_MENU("Spaceship.wav", 1.0f), + LOBBY("DeadPlanet.wav", 1.0f), + CEREMONY("80s,Disco,Life.wav", 1.0f), + GAME_1("NeonRoadTrip.wav", false, 1.0f), + GAME_2("NoPressureTrance.wav", false, 1.0f), + GAME_3("TheSynthRave.wav", false, 1.0f), + GAME_4("LaserParty.wav", false, 1.0f), + GAME_5("RetroNoir.wav", false, 1.0f), + GAME_6("SpaceInvaders.wav", false, 1.0f); + + private final String path; + private final boolean loop; + private final float subVolume; + + /** + * Constructs a new MusicAsset object with the specified name and sub-volume. + * The track will not loop by default. + * + * @param name The name of the music file. + * @param subVolume A relative volume that modifies the base volume of the track (typically a percentage). + */ + MusicAsset(String name, float subVolume) { + this.path = "music/" + name; + this.loop = false; + this.subVolume = subVolume; + } + + /** + * Constructs a new MusicAsset object with the specified name, loop flag, and sub-volume. + * + * @param name The name of the music file. + * @param loop If true, the track will loop; otherwise, it will play once. + * @param subVolume A relative volume that modifies the base volume of the track (typically a percentage). + */ + MusicAsset(String name, boolean loop, float subVolume) { + this.path = "music/" + name; + this.loop = loop; + this.subVolume = subVolume; + } + + /** + * Gets the file path of the music track. + * + * @return The path to the music file (relative to the music folder). + */ + public String getPath() { + return path; + } + + /** + * Gets whether the music track should loop. + * + * @return true if the track should loop, false otherwise. + */ + public boolean getLoop() { + return loop; + } + + /** + * Gets the relative volume (subVolume) for the music track. + * + * @return The relative volume for the track, typically a value between 0.0 and 1.0. + */ + public float getSubVolume() { + return subVolume; + } +} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/SoundAsset.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/SoundAsset.java new file mode 100644 index 00000000..32749c3c --- /dev/null +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/SoundAsset.java @@ -0,0 +1,41 @@ +package pp.mdga.client.Acoustic; + +/** + * Enum representing various sound assets used in the game. + * Each constant corresponds to a specific sound effect used throughout the game. + * These sounds are associated with various events and actions, such as dice rolls, + * turn changes, piece movements, and game outcomes. + */ +enum SoundAsset { + DICE_ROLL(""), + TURN_START(""), + TURN_END(""), + PIECE_END(""), + PIECE_MOVE(""), + PIECE_LOST(""), + SELECT(""), + DESELECT(""), + HURRY(""), + VICTORY("LevelUp2.wav"), + LOST("GameOver.wav"); + + private final String path; + + /** + * Constructs a new SoundAsset object with the specified name. + * + * @param name The name of the sound file. + */ + SoundAsset(String name) { + this.path = "sound/" + name; + } + + /** + * Gets the file path of the sound effect. + * + * @return The path to the sound file (relative to the sound folder). + */ + public String getPath() { + return path; + } +} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/SoundAssetDelayVolume.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/SoundAssetDelayVolume.java new file mode 100644 index 00000000..a9f1dfbf --- /dev/null +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Acoustic/SoundAssetDelayVolume.java @@ -0,0 +1,7 @@ +package pp.mdga.client.Acoustic; + +/** + * A record that encapsulates a sound asset along with its playback settings: + * the relative volume (subVolume) and a delay before it starts playing. + */ +record SoundAssetDelayVolume(SoundAsset asset, float subVolume, float delay) {} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/Animation.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/Animation.java index 0ca7adcb..32aadbc4 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/Animation.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/Animation.java @@ -2,6 +2,8 @@ abstract class Animation { abstract void play(); + abstract void stop(); + abstract boolean isOver(); } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/AnimationHandler.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/AnimationHandler.java index 7047fff5..1fdf223d 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/AnimationHandler.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/AnimationHandler.java @@ -11,19 +11,19 @@ public AnimationHandler(MdgaApp app) { this.app = app; } - public void playAnimation(AnimationType type) { + public void playAnimation(MdgaAnimation type) { } public void update() { - if(null == animation) { + if (null == animation) { return; } - if(animation.isOver()) { + if (animation.isOver()) { animation = null; - //trigger next state + //trigger next state in model } } } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/AnimationType.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/MdgaAnimation.java similarity index 56% rename from Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/AnimationType.java rename to Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/MdgaAnimation.java index 5d2d0233..4d1e0fff 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/AnimationType.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Animation/MdgaAnimation.java @@ -1,4 +1,4 @@ package pp.mdga.client.Animation; -public enum AnimationType { +public enum MdgaAnimation { } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/AssetOnMap.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/AssetOnMap.java new file mode 100644 index 00000000..c86364f8 --- /dev/null +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/AssetOnMap.java @@ -0,0 +1,3 @@ +package pp.mdga.client.Board; + +record AssetOnMap(BoardAsset asset, int x, int y, float rot) {} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Asset.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/BoardAsset.java similarity index 79% rename from Projekte/mdga/client/src/main/java/pp/mdga/client/Asset.java rename to Projekte/mdga/client/src/main/java/pp/mdga/client/Board/BoardAsset.java index 25ac35f3..70f850f5 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/Asset.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/BoardAsset.java @@ -1,6 +1,6 @@ -package pp.mdga.client; +package pp.mdga.client.Board; -public enum Asset { +enum BoardAsset { bigTent, cardStack, cir, @@ -8,13 +8,13 @@ public enum Asset { jet, lw, marine, - node_home_blue("./node_home/node_home.j3o", "./node_home/node_home_blue.png"), - node_home_black("./node_home/node_home.j3o", "./node_home/node_home_black.png"), - node_home_green("./node_home/node_home.j3o", "./node_home/node_home_green.png"), - node_home_yellow("./node_home/node_home.j3o", "./node_home/node_home_yellow.png"), + node_home_blue("./node_home/node_home.j3o", "./node_home/node_home_blue_diff.png"), + node_home_black("./node_home/node_home.j3o", "./node_home/node_home_black_diff.png"), + node_home_green("./node_home/node_home.j3o", "./node_home/node_home_green_diff.png"), + node_home_yellow("./node_home/node_home.j3o", "./node_home/node_home_yellow_diff.png"), node_normal, - node_start("./node_normal/node_normal.j3o", "./node_normal/node_normal_start.png"), - node_bonus("./node_normal/node_normal.j3o", "./node_normal/node_normal_bonus.png"), + node_start("./node_normal/node_normal.j3o", "./node_normal/node_start_diff.png"), + node_bonus("./node_normal/node_normal.j3o", "./node_normal/node_bonus_diff.png"), radar, shieldCard, ship, @@ -22,26 +22,26 @@ public enum Asset { swapCard, tank, turboCard, - world(1.1f); + world(1.2f); private final String modelPath; private final String diffPath; private final float size; - Asset(){ + BoardAsset() { String folderFileName = "./" + name() + "/" + name(); this.modelPath = folderFileName + ".j3o"; this.diffPath = folderFileName + "_diff.png"; this.size = 1f; } - Asset(String modelPath, String diffPath){ + BoardAsset(String modelPath, String diffPath) { this.modelPath = modelPath; this.diffPath = diffPath; this.size = 1f; } - Asset(float size){ + BoardAsset(float size) { String folderFileName = "./" + name() + "/" + name(); this.modelPath = folderFileName + ".j3o"; this.diffPath = folderFileName + "_diff.png"; @@ -56,8 +56,7 @@ public String getDiffPath() { return diffPath; } - public float getSize(){ + public float getSize() { return size; } - } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/BoardView.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/BoardView.java index 7bbd1f1e..e652faf7 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/BoardView.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/BoardView.java @@ -1,30 +1,140 @@ package pp.mdga.client.Board; +import com.jme3.light.AmbientLight; +import com.jme3.light.DirectionalLight; +import com.jme3.material.Material; +import com.jme3.math.ColorRGBA; import com.jme3.math.Vector3f; +import com.jme3.renderer.queue.RenderQueue; +import com.jme3.scene.Spatial; +import com.jme3.scene.control.AbstractControl; +import com.jme3.shadow.DirectionalLightShadowRenderer; +import pp.mdga.client.MdgaApp; +import pp.mdga.game.Color; -import java.util.ArrayList; +import java.util.*; public class BoardView { - private static final float GRID_SIZE = 10.0f; + private static final float GRID_SIZE = 1.72f; private static final float GRID_ELEVATION = 0.0f; - private static final int GRID_EXTEND = 5; + private static final String MAP_NAME = "map.mdga"; - private PileControl drawPile = new PileControl(); - private PileControl discardPile = new PileControl(); + private final MdgaApp app; - private ArrayList infield = new ArrayList(40); - private ArrayList pieces; + private PileControl drawPile = null; + private PileControl discardPile = null; - BoardView(int playerCount) { - assert(2 <= playerCount && playerCount <= 4); + private ArrayList infield = new ArrayList<>(40); + private Map pieces; - pieces = new ArrayList(4 * playerCount); + private Map> playerMap; + + public BoardView(MdgaApp app) { + assert (app != null) : "app is null"; + + this.app = app; + + this.pieces = new HashMap<>(); + this.playerMap = new HashMap<>(); + + initMap(); + initCamera(); + } + + private void addFigureToPlayerMap(Color col, AssetOnMap assetOnMap) { + List inMap = playerMap.getOrDefault(col, new ArrayList<>()); + inMap.add(assetOnMap); + + assert (inMap.size() <= 4) : "to many assets for one player"; + + playerMap.put(col, inMap); + } + + private void initMap() { + List assetOnMaps = MapLoader.loadMap(MAP_NAME); + + for (AssetOnMap assetOnMap : assetOnMaps) { + switch (assetOnMap.asset()) { + case lw -> addFigureToPlayerMap(assetToColor(BoardAsset.lw), assetOnMap); + case heer -> addFigureToPlayerMap(assetToColor(BoardAsset.heer), assetOnMap); + case cir -> addFigureToPlayerMap(assetToColor(BoardAsset.cir), assetOnMap); + case marine -> addFigureToPlayerMap(assetToColor(BoardAsset.marine), assetOnMap); + case node_normal, node_bonus, node_start -> + infield.addLast(displayAndControl(assetOnMap, new NodeControl())); + default -> displayAsset(assetOnMap); + } + } + } + + private void initCamera() { + app.getFlyByCamera().setEnabled(true); + int zoom = 20; + app.getCamera().setLocation(new Vector3f(-zoom, 0, zoom)); + app.getCamera().lookAt(new Vector3f(0, 0, 0), new Vector3f(0, 0, 1)); + + DirectionalLight sun = new DirectionalLight(); + sun.setColor(ColorRGBA.White); + sun.setDirection(new Vector3f(0.3f, 0, -1)); + app.getRootNode().addLight(sun); + + AmbientLight ambient = new AmbientLight(); + ambient.setColor(new ColorRGBA(0.3f, 0.3f, 0.3f, 1)); + app.getRootNode().addLight(ambient); + + int SHADOWMAP_SIZE = 1024 * 8; + DirectionalLightShadowRenderer dlsr = new DirectionalLightShadowRenderer(app.getAssetManager(), SHADOWMAP_SIZE, 4); + dlsr.setLight(sun); + app.getViewPort().addProcessor(dlsr); + } + + private Color assetToColor(BoardAsset asset) { + return switch (asset) { + case lw -> Color.AIRFORCE; + case heer -> Color.ARMY; + case marine -> Color.NAVY; + case cir -> Color.CYBER; + default -> throw new RuntimeException("invalid asset"); + }; + } + + private Spatial createModel(BoardAsset asset, Vector3f pos, float rot) { + String modelName = asset.getModelPath(); + String texName = asset.getDiffPath(); + Spatial model = app.getAssetManager().loadModel(modelName); + model.scale(asset.getSize()); + model.rotate((float) Math.toRadians(0), 0, (float) Math.toRadians(90 + rot)); + model.setLocalTranslation(pos); + model.setShadowMode(RenderQueue.ShadowMode.CastAndReceive); + Material mat = new Material(app.getAssetManager(), "Common/MatDefs/Light/Lighting.j3md"); + mat.setTexture("DiffuseMap", app.getAssetManager().loadTexture(texName)); + model.setMaterial(mat); + app.getRootNode().attachChild(model); + return model; } private static Vector3f gridToWorld(int x, int y) { - assert(-GRID_EXTEND <= x && x <= GRID_EXTEND); - assert(-GRID_EXTEND <= y && y < GRID_EXTEND); + return new Vector3f(GRID_SIZE * x, GRID_SIZE * y, GRID_ELEVATION); + } - return new Vector3f(GRID_SIZE * x, GRID_ELEVATION, GRID_SIZE * y); + public void addPlayer(Color color, UUID uuid) { + List playerAssets = playerMap.get(color); + assert (playerAssets != null) : "Assets for Player color are not defined"; + + for (AssetOnMap assetOnMap : playerAssets) { + pieces.put(uuid, displayAndControl(assetOnMap, new PieceControl())); + } + } + + //displays an assets and return the created asset + private Spatial displayAsset(AssetOnMap assetOnMap) { + int x = assetOnMap.x(); + int y = assetOnMap.y(); + return createModel(assetOnMap.asset(), gridToWorld(x, y), assetOnMap.rot()); + } + + private T displayAndControl(AssetOnMap assetOnMap, T control) { + Spatial spatial = displayAsset(assetOnMap); + spatial.addControl(control); + return control; } } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/MapLoader.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/MapLoader.java new file mode 100644 index 00000000..d6a30228 --- /dev/null +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/MapLoader.java @@ -0,0 +1,83 @@ +package pp.mdga.client.Board; + +import java.io.BufferedReader; +import java.io.IOException; +import java.io.InputStream; +import java.io.InputStreamReader; +import java.util.ArrayList; +import java.util.List; + +class MapLoader { + private MapLoader() { + + } + + public static List loadMap(String mapName) { + List assetsOnMap = new ArrayList<>(); + + try ( + InputStream inputStream = MapLoader.class.getClassLoader().getResourceAsStream(mapName); + BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream)) + ) { + + while (true) { + String entry = reader.readLine(); + if (entry == null) break; + + entry = entry.trim(); + + if (entry.isEmpty()) continue; + if (entry.charAt(0) == '#') continue; + + String[] parts = entry.trim().split(" "); + + assert (parts.length == 3) : "MapLoader: line has not 3 parts"; + + String assetName = parts[0]; + String[] coordinates = parts[1].split(","); + + assert (coordinates.length == 2) : "MapLoade: coordinates are wrong"; + + int x = Integer.parseInt(coordinates[0]); + int y = Integer.parseInt(coordinates[1]); + + float rot = Float.parseFloat(parts[2]); + + BoardAsset asset = getLoadedAsset(assetName); + assetsOnMap.add(new AssetOnMap(asset, x, y, rot)); + } + } + catch (IOException e) { + e.printStackTrace(); + } + catch (IllegalArgumentException e) { + e.printStackTrace(); + } + + return assetsOnMap; + } + + private static BoardAsset getLoadedAsset(String assetName) { + return switch (assetName) { + case "lw" -> BoardAsset.lw; + case "cir" -> BoardAsset.cir; + case "marine" -> BoardAsset.marine; + case "heer" -> BoardAsset.heer; + case "node" -> BoardAsset.node_normal; + case "node_start" -> BoardAsset.node_start; + case "node_bonus" -> BoardAsset.node_bonus; + case "node_home_blue" -> BoardAsset.node_home_blue; + case "node_home_yellow" -> BoardAsset.node_home_yellow; + case "node_home_black" -> BoardAsset.node_home_black; + case "node_home_green" -> BoardAsset.node_home_green; + case "world" -> BoardAsset.world; + case "jet" -> BoardAsset.jet; + case "big_tent" -> BoardAsset.bigTent; + case "small_tent" -> BoardAsset.smallTent; + case "radar" -> BoardAsset.radar; + case "ship" -> BoardAsset.ship; + case "tank" -> BoardAsset.tank; + default -> throw new IllegalStateException("Unexpected value: " + assetName); + }; + } +} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/NodeControl.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/NodeControl.java index 6e8ecfa1..d3710e6e 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/NodeControl.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/NodeControl.java @@ -1,5 +1,18 @@ package pp.mdga.client.Board; -public class NodeControl { +import com.jme3.renderer.RenderManager; +import com.jme3.renderer.ViewPort; +import com.jme3.scene.control.AbstractControl; +public class NodeControl extends AbstractControl { + + @Override + protected void controlUpdate(float v) { + + } + + @Override + protected void controlRender(RenderManager renderManager, ViewPort viewPort) { + + } } 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 4ef15526..689411d7 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 @@ -1,5 +1,18 @@ package pp.mdga.client.Board; -public class PieceControl { +import com.jme3.renderer.RenderManager; +import com.jme3.renderer.ViewPort; +import com.jme3.scene.control.AbstractControl; +public class PieceControl extends AbstractControl { + + @Override + protected void controlUpdate(float v) { + + } + + @Override + protected void controlRender(RenderManager renderManager, ViewPort viewPort) { + + } } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/PileControl.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/PileControl.java index 4cdc7db1..67a4d994 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/PileControl.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Board/PileControl.java @@ -1,5 +1,5 @@ package pp.mdga.client.Board; -public class PileControl { +class PileControl { } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Dialog/DialogView.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Dialog/DialogView.java index 462da741..88d6b76a 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/Dialog/DialogView.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Dialog/DialogView.java @@ -1,5 +1,26 @@ package pp.mdga.client.Dialog; -public class DialogView { +import pp.dialog.DialogManager; +import pp.mdga.client.MdgaApp; +public class DialogView { + private MdgaApp app; + + private DialogManager dialogManager = new DialogManager(app); + + private StartDialog dialog; + + public DialogView(MdgaApp app) { + this.app = app; + } + + DialogManager getDialogManager() { + return dialogManager; + } + + public void mainMenu() { + //dialogManager = new DialogManager(app); + //di + //MainMenuDialog mainMenuDialog = new MainMenuDialog(app); + } } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Dialog/InterruptDialog.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Dialog/InterruptDialog.java new file mode 100644 index 00000000..917a9401 --- /dev/null +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Dialog/InterruptDialog.java @@ -0,0 +1,4 @@ +package pp.mdga.client.Dialog; + +public class InterruptDialog { +} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/Dialog/StartDialog.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/Dialog/StartDialog.java index 76a8c0fc..23d7f6f3 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/Dialog/StartDialog.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/Dialog/StartDialog.java @@ -1,5 +1,34 @@ package pp.mdga.client.Dialog; -public class StartDialog { +import com.simsilica.lemur.Checkbox; +import com.simsilica.lemur.Container; +import com.simsilica.lemur.Label; +import com.simsilica.lemur.component.SpringGridLayout; +import pp.dialog.DialogBuilder; +import pp.dialog.SimpleDialog; +import pp.mdga.client.MdgaApp; +public class StartDialog extends SimpleDialog { + StartDialog(MdgaApp app) { + super(app.getDialogView().getDialogManager()); + + Checkbox serverHost = new Checkbox("sdgfsdg"); + serverHost.setChecked(false); + //serverHost.addClickCommands(s -> toggleServerHost()); + + final Container input = new Container(new SpringGridLayout()); + input.addChild(new Label("sdgsgsdg")); + //input.addChild(host, 1); + input.addChild(new Label("sdfdsgsdgsdg")); + //input.addChild(port, 1); + input.addChild(serverHost); + + DialogBuilder.simple(app.getDialogView().getDialogManager()) + .setTitle("server.dialog") + .setOkButton("button.connect") + .setNoButton("button.cancel") + .setOkClose(false) + .setNoClose(false) + .build(this); + } } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/MdgaApp.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/MdgaApp.java index 1567ee4f..479e485d 100644 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/MdgaApp.java +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/MdgaApp.java @@ -1,29 +1,31 @@ package pp.mdga.client; import com.jme3.app.SimpleApplication; -import com.jme3.renderer.RenderManager; +import com.jme3.system.NanoTimer; +import pp.mdga.client.Acoustic.AcousticHandler; +import pp.mdga.client.Acoustic.MdgaSound; import pp.mdga.client.Animation.AnimationHandler; -import com.jme3.light.AmbientLight; -import com.jme3.light.DirectionalLight; -import com.jme3.material.Material; -import com.jme3.math.ColorRGBA; -import com.jme3.math.Vector3f; -import com.jme3.renderer.RenderManager; -import com.jme3.renderer.queue.RenderQueue; -import com.jme3.scene.Spatial; -import com.jme3.shadow.DirectionalLightShadowRenderer; import com.jme3.system.AppSettings; +import pp.mdga.client.Board.BoardView; +import pp.mdga.client.Dialog.DialogView; public class MdgaApp extends SimpleApplication { private AnimationHandler animationHandler; + private AcousticHandler acousticHandler; + private BoardView boardView; + private DialogView dialogView; + + NanoTimer test = new NanoTimer(); + private MdgaState testState = MdgaState.MAIN; public static void main(String[] args) { - MdgaApp app = new MdgaApp(); AppSettings settings = new AppSettings(true); settings.setSamples(128); settings.setCenterWindow(true); - settings.setWidth(1300); - settings.setHeight(1000); + settings.setWidth(1280); + settings.setHeight(720); + + MdgaApp app = new MdgaApp(); app.setSettings(settings); app.setShowSettings(false); app.start(); @@ -32,60 +34,53 @@ public static void main(String[] args) { @Override public void simpleInitApp() { animationHandler = new AnimationHandler(this); + acousticHandler = new AcousticHandler(this); + boardView = new BoardView(this); + dialogView = new DialogView(this); - flyCam.setEnabled(true); - int zoom = 20; - cam.setLocation(new Vector3f(zoom,0,zoom)); - cam.lookAt(new Vector3f(0,0,0), new Vector3f(0,0,1)); + //dialogView.mainMenu(); + //acousticHandler.playState(MdgaState.GAME); - DirectionalLight sun = new DirectionalLight(); - sun.setColor(ColorRGBA.White); - sun.setDirection(new Vector3f(-1,0,-1)); - rootNode.addLight(sun); - AmbientLight ambient = new AmbientLight(); - ambient.setColor(new ColorRGBA(0.3f,0.3f,0.3f,1)); - rootNode.addLight(ambient); - - final int SHADOWMAP_SIZE=1024*8; - DirectionalLightShadowRenderer dlsr = new DirectionalLightShadowRenderer(assetManager, SHADOWMAP_SIZE, 4); - dlsr.setLight(sun); - viewPort.addProcessor(dlsr); - - createModel(Asset.lw).setLocalTranslation(new Vector3f(0,-10,0)); - createModel(Asset.cir).setLocalTranslation(new Vector3f(0,-8,0)); - createModel(Asset.marine).setLocalTranslation(new Vector3f(0,-6,0)); - createModel(Asset.heer).setLocalTranslation(new Vector3f(0,-4,0)); - createModel(Asset.node_normal).setLocalTranslation(new Vector3f(0,-2.5f,0)); - createModel(Asset.node_home_blue).setLocalTranslation(new Vector3f(0,-1,0)); - createModel(Asset.smallTent).setLocalTranslation(new Vector3f(0,1,0)); - createModel(Asset.tank).setLocalTranslation(new Vector3f(0,5,0)); - createModel(Asset.jet).setLocalTranslation(new Vector3f(0,12,0)); - createModel(Asset.ship).setLocalTranslation(new Vector3f(0,17,0)); - createModel(Asset.radar).setLocalTranslation(new Vector3f(0,20,0)); - - createModel(Asset.world); - - //System.out.println(Asset.node_normal.getModelPath()); - //System.out.println(Asset.node_normal.getDiffPath()); - } - - - private Spatial createModel(Asset asset){ - String modelName = asset.getModelPath(); - String texName = asset.getDiffPath(); - Spatial model = assetManager.loadModel(modelName); - model.scale(asset.getSize()); - model.rotate((float) Math.toRadians(0), 0, (float) Math.toRadians(90)); - model.setShadowMode(RenderQueue.ShadowMode.CastAndReceive); - Material mat = new Material(assetManager, "Common/MatDefs/Light/Lighting.j3md"); - mat.setTexture("DiffuseMap", assetManager.loadTexture(texName)); - model.setMaterial(mat); - rootNode.attachChild(model); - return model; + acousticHandler.playSound(MdgaSound.LOST); + acousticHandler.playSound(MdgaSound.VICTORY); } @Override public void simpleUpdate(float tpf) { - //this method will be called every game tick and can be used to make updates + acousticHandler.update(); + + //test.reset(); + if (test.getTimeInSeconds() > 10) { + if (testState == MdgaState.MAIN) { + testState = MdgaState.LOBBY; + acousticHandler.playState(MdgaState.MAIN); + } + else if (testState == MdgaState.LOBBY) { + testState = MdgaState.CEREMONY; + acousticHandler.playState(MdgaState.LOBBY); + } + else { + testState = MdgaState.MAIN; + acousticHandler.playState(MdgaState.CEREMONY); + } + + test.reset(); + } + } + + public AnimationHandler getAnimationHandler() { + return animationHandler; + } + + public AcousticHandler getAcousticHandler() { + return acousticHandler; + } + + public BoardView getBoardView() { + return boardView; + } + + public DialogView getDialogView() { + return dialogView; } } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/MdgaState.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/MdgaState.java new file mode 100644 index 00000000..d178bce7 --- /dev/null +++ b/Projekte/mdga/client/src/main/java/pp/mdga/client/MdgaState.java @@ -0,0 +1,48 @@ +package pp.mdga.client; + +import pp.mdga.notification.Notification; +import pp.mdga.notification.PieceInGameNotification; +import pp.mdga.notification.PlayerInGameNotification; + +public enum MdgaState { + NONE { + @Override + void handleNotification(MdgaApp app, Notification notification) { + throw new RuntimeException("unexpected notification"); + } + }, + MAIN { + @Override + void handleNotification(MdgaApp app, Notification notification) { + throw new RuntimeException("unexpected notification"); + } + }, + LOBBY { + @Override + void handleNotification(MdgaApp app, Notification notification) { + throw new RuntimeException("unexpected notification"); + } + }, + GAME { + @Override + void handleNotification(MdgaApp app, Notification notification) { + if (notification instanceof PlayerInGameNotification) { + //TODO + } + else if (notification instanceof PieceInGameNotification) { + //TODO + } + else { + throw new RuntimeException("unexpected notification"); + } + } + }, + CEREMONY { + @Override + void handleNotification(MdgaApp app, Notification notification) { + throw new RuntimeException("unexpected notification"); + } + }; + + abstract void handleNotification(MdgaApp app, Notification notification); +} 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 8c3e5135..2a95a2a7 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 @@ -1,5 +1,23 @@ package pp.mdga.client; -public class NotificationSynchronizer { +import pp.mdga.notification.Notification; +import java.util.ArrayList; + +public class NotificationSynchronizer { + private final MdgaApp app; + private MdgaState state = MdgaState.MAIN; + + NotificationSynchronizer(MdgaApp app) { + this.app = app; + } + + void update() { + ArrayList notifications = new ArrayList<>(); + //TODO fetch model notifications + + for (Notification n : notifications) { + state.handleNotification(app, n); + } + } } diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/CeremonyState.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/State/CeremonyState.java deleted file mode 100644 index 47b40346..00000000 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/CeremonyState.java +++ /dev/null @@ -1,5 +0,0 @@ -package pp.mdga.client.State; - -public class CeremonyState { - -} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/GameState.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/State/GameState.java deleted file mode 100644 index deddeb1d..00000000 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/GameState.java +++ /dev/null @@ -1,5 +0,0 @@ -package pp.mdga.client.State; - -public class GameState { - -} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/LobbyState.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/State/LobbyState.java deleted file mode 100644 index 58777b55..00000000 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/LobbyState.java +++ /dev/null @@ -1,5 +0,0 @@ -package pp.mdga.client.State; - -public class LobbyState { - -} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/MdgaState.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/State/MdgaState.java deleted file mode 100644 index 8476a7af..00000000 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/MdgaState.java +++ /dev/null @@ -1,5 +0,0 @@ -package pp.mdga.client.State; - -public class MdgaState { - -} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/MusicState.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/State/MusicState.java deleted file mode 100644 index b1e5484d..00000000 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/MusicState.java +++ /dev/null @@ -1,5 +0,0 @@ -package pp.mdga.client.State; - -public class MusicState { - -} diff --git a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/SoundState.java b/Projekte/mdga/client/src/main/java/pp/mdga/client/State/SoundState.java deleted file mode 100644 index f3184745..00000000 --- a/Projekte/mdga/client/src/main/java/pp/mdga/client/State/SoundState.java +++ /dev/null @@ -1,5 +0,0 @@ -package pp.mdga.client.State; - -public class SoundState { - -} diff --git a/Projekte/mdga/client/src/main/resources/circle_map.mdga b/Projekte/mdga/client/src/main/resources/circle_map.mdga new file mode 100644 index 00000000..71c74643 --- /dev/null +++ b/Projekte/mdga/client/src/main/resources/circle_map.mdga @@ -0,0 +1,66 @@ +world 0,0 + +# jet 0,0 + +#Nodes für Map +node_start 8,0 +node 8,1 +node 8,2 +node 7,3 +node_bonus 6,4 +node 5,5 +node 4,6 +node 3,7 +node 2,8 +node 1,8 +node_start 0,8 +node -1,8 +node -2,8 +node -3,7 +node_bonus -4,6 +node -5,5 +node -6,4 +node -7,3 +node -8,2 +node -8,1 +node_start -8,0 +node -8,-1 +node -8,-2 +node -7,-3 +node_bonus -6,-4 +node -5,-5 +node -4,-6 +node -3,-7 +node -2,-8 +node -1,-8 +node_start 0,-8 +node 1,-8 +node 2,-8 +node 3,-7 +node_bonus 4,-6 +node 5,-5 +node 6,-4 +node 7,-3 +node 8,-2 +node 8,-1 + +#Node Home +node_home_blue 7,0 +node_home_blue 6,0 +node_home_blue 5,0 +node_home_blue 4,0 + +node_home_black 0,4 +node_home_black 0,5 +node_home_black 0,6 +node_home_black 0,7 + +node_home_yellow 0,-4 +node_home_yellow 0,-5 +node_home_yellow 0,-6 +node_home_yellow 0,-7 + +node_home_green -4,0 +node_home_green -5,0 +node_home_green -6,0 +node_home_green -7,0 diff --git a/Projekte/mdga/client/src/main/resources/map.mdga b/Projekte/mdga/client/src/main/resources/map.mdga new file mode 100644 index 00000000..cf955999 --- /dev/null +++ b/Projekte/mdga/client/src/main/resources/map.mdga @@ -0,0 +1,126 @@ +world 0,0 0 + +#Marine Pos +marine 4,-5 180 +marine 4,-4 180 +marine 5,-4 180 +marine 5,-5 180 + +#Blue (Marine) Home Node +node_home_blue 4,-5 0 +node_home_blue 4,-4 0 +node_home_blue 5,-4 0 +node_home_blue 5,-5 0 + +#Lw Pos +lw -5,4 0 +lw -4,4 0 +lw -4,5 0 +lw -5,5 0 + +#Black (Lw) Home Node +node_home_black -5,4 0 +node_home_black -4,4 0 +node_home_black -4,5 0 +node_home_black -5,5 0 + +#Heer Pos +heer -4,-5 90 +heer -4,-4 90 +heer -5,-4 90 +heer -5,-5 90 + +#Green (Heer) Home Node +node_home_green -4,-5 0 +node_home_green -4,-4 0 +node_home_green -5,-4 0 +node_home_green -5,-5 0 + +#CIR Pos +cir 4,5 -90 +cir 4,4 -90 +cir 5,4 -90 +cir 5,5 -90 + +#Assets +jet -10,-1 -45 +ship 11,0 79 +big_tent -9,-7 40 +big_tent 7,-10 135 +small_tent -9,7 -45 +small_tent -10,5 -30 +radar 0,10 -110 +small_tent 6,8 100 +small_tent 8,7 70 +tank -1,-10 45 + + +#Yellow (CIR) Home Node +node_home_yellow 4,5 0 +node_home_yellow 4,4 0 +node_home_yellow 5,4 0 +node_home_yellow 5,5 0 + +#Nodes für Map +node_start -5,1 0 +node -4,1 0 +node -3,1 0 +node -2,1 0 +node_bonus -1,1 0 +node -1,2 0 +node -1,3 0 +node -1,4 0 +node -1,5 0 +node 0,5 0 +node_start 1,5 0 +node 1,4 0 +node 1,3 0 +node 1,2 0 +node_bonus 1,1 0 +node 2,1 0 +node 3,1 0 +node 4,1 0 +node 5,1 0 +node 5,0 0 +node_start 5,-1 0 +node 4,-1 0 +node 3,-1 0 +node 2,-1 0 +node_bonus 1,-1 0 +node 1,-2 0 +node 1,-3 0 +node 1,-4 0 +node 1,-5 0 +node 0,-5 0 +node_start -1,-5 0 +node -1,-4 0 +node -1,-3 0 +node -1,-2 0 +node_bonus -1,-1 0 +node -2,-1 0 +node -3,-1 0 +node -4,-1 0 +node -5,-1 0 +node -5,0 0 + + +#Node Home +node_home_green 0,-1 0 +node_home_green 0,-2 0 +node_home_green 0,-3 0 +node_home_green 0,-4 0 + +node_home_yellow 0,1 0 +node_home_yellow 0,2 0 +node_home_yellow 0,3 0 +node_home_yellow 0,4 0 + +node_home_blue 1,0 0 +node_home_blue 2,0 0 +node_home_blue 3,0 0 +node_home_blue 4,0 0 + +node_home_black -1,0 0 +node_home_black -2,0 0 +node_home_black -3,0 0 +node_home_black -4,0 0 diff --git a/Projekte/mdga/client/src/main/resources/music/80s,Disco,Life.wav b/Projekte/mdga/client/src/main/resources/music/80s,Disco,Life.wav new file mode 100644 index 00000000..9f394d8b Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/music/80s,Disco,Life.wav differ diff --git a/Projekte/mdga/client/src/main/resources/music/CREDIT.txt b/Projekte/mdga/client/src/main/resources/music/CREDIT.txt new file mode 100644 index 00000000..487d2c13 --- /dev/null +++ b/Projekte/mdga/client/src/main/resources/music/CREDIT.txt @@ -0,0 +1,22 @@ +# Credit + +## Free SynthWave Music Pack + +See "Free SynthWave Music Pack License.pdf" for LICENCE information. + + - 80s,Dico,Live.wav + - LaserParty.wav + - NeonRoadTrip.wav + - NoPressureTrance.wav + - RetroNoir.wav + - SpaceInvaders.wav + - TheSynthRave.SynthWave + +## Short Loopable Background Music + + https://joshuuu.itch.io/short-loopable-background-music + + Free for personal or commercial use as long as you don't redistribute as your own. Donations also welcome! Please add jhaeka to your credits. :) + + - DeadPlanet.wav + - Spaceship.wav diff --git a/Projekte/mdga/client/src/main/resources/music/DeadPlanet.wav b/Projekte/mdga/client/src/main/resources/music/DeadPlanet.wav new file mode 100644 index 00000000..98d78964 Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/music/DeadPlanet.wav differ diff --git a/Projekte/mdga/client/src/main/resources/music/Free SynthWave Music Pack License.pdf b/Projekte/mdga/client/src/main/resources/music/Free SynthWave Music Pack License.pdf new file mode 100644 index 00000000..de1833e4 Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/music/Free SynthWave Music Pack License.pdf differ diff --git a/Projekte/mdga/client/src/main/resources/music/LaserParty.wav b/Projekte/mdga/client/src/main/resources/music/LaserParty.wav new file mode 100644 index 00000000..7b1545f4 Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/music/LaserParty.wav differ diff --git a/Projekte/mdga/client/src/main/resources/music/NeonRoadTrip.wav b/Projekte/mdga/client/src/main/resources/music/NeonRoadTrip.wav new file mode 100644 index 00000000..6f686d35 Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/music/NeonRoadTrip.wav differ diff --git a/Projekte/mdga/client/src/main/resources/music/NoPressureTrance.wav b/Projekte/mdga/client/src/main/resources/music/NoPressureTrance.wav new file mode 100644 index 00000000..9a67bc39 Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/music/NoPressureTrance.wav differ diff --git a/Projekte/mdga/client/src/main/resources/music/RetroNoir.wav b/Projekte/mdga/client/src/main/resources/music/RetroNoir.wav new file mode 100644 index 00000000..c7415be5 Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/music/RetroNoir.wav differ diff --git a/Projekte/mdga/client/src/main/resources/music/SpaceInvaders.wav b/Projekte/mdga/client/src/main/resources/music/SpaceInvaders.wav new file mode 100644 index 00000000..ee24985c Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/music/SpaceInvaders.wav differ diff --git a/Projekte/mdga/client/src/main/resources/music/Spaceship.wav b/Projekte/mdga/client/src/main/resources/music/Spaceship.wav new file mode 100644 index 00000000..d9be3316 Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/music/Spaceship.wav differ diff --git a/Projekte/mdga/client/src/main/resources/music/SynthWave Music Pack Square.png b/Projekte/mdga/client/src/main/resources/music/SynthWave Music Pack Square.png new file mode 100644 index 00000000..e6e07e8a Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/music/SynthWave Music Pack Square.png differ diff --git a/Projekte/mdga/client/src/main/resources/music/TheSynthRave.wav b/Projekte/mdga/client/src/main/resources/music/TheSynthRave.wav new file mode 100644 index 00000000..512c6160 Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/music/TheSynthRave.wav differ diff --git a/Projekte/mdga/client/src/main/resources/node_home/node_home_blue.png b/Projekte/mdga/client/src/main/resources/node_home/node_home_blue_diff.png similarity index 100% rename from Projekte/mdga/client/src/main/resources/node_home/node_home_blue.png rename to Projekte/mdga/client/src/main/resources/node_home/node_home_blue_diff.png diff --git a/Projekte/mdga/client/src/main/resources/sound/GameOver.wav b/Projekte/mdga/client/src/main/resources/sound/GameOver.wav new file mode 100644 index 00000000..08b99121 Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/sound/GameOver.wav differ diff --git a/Projekte/mdga/client/src/main/resources/sound/LevelUp2.wav b/Projekte/mdga/client/src/main/resources/sound/LevelUp2.wav new file mode 100644 index 00000000..53483a34 Binary files /dev/null and b/Projekte/mdga/client/src/main/resources/sound/LevelUp2.wav differ diff --git a/Projekte/settings.gradle b/Projekte/settings.gradle index 532a4d06..225769d5 100644 --- a/Projekte/settings.gradle +++ b/Projekte/settings.gradle @@ -32,8 +32,8 @@ } } } -include 'mdga:client' -findProject(':mdga:client')?.name = 'client' -include 'mdga:client' -findProject(':mdga:client')?.name = 'client' + +include 'mdga:client' +include 'mdga:model' +findProject(':mdga:client')?.name = 'client'