diff --git a/Extensions/ArchExtensions.cs b/Extensions/ArchExtensions.cs index a01a3af..91f4750 100644 --- a/Extensions/ArchExtensions.cs +++ b/Extensions/ArchExtensions.cs @@ -21,6 +21,14 @@ public static Entity QueryFirst(this World world) return result.Value; } + public static Entity? QueryFirstOrNull(this World world) + { + try { return world.QueryFirst(); } + catch + { + return null; + } + } public static T0 QueryUnique(this World world) where T0 : struct { diff --git a/Readme.md b/Readme.md index 85d659e..46f1cfc 100644 --- a/Readme.md +++ b/Readme.md @@ -4,7 +4,7 @@ A Game for [Game of the Month 29 (November 2023)](https://itch.io/jam/one-game-a # How to play -Download the latest release from [the Releases](https://github.com/Nhawdge/November-Pirates/releases]. +Download the latest release from [itch](https://nhawdge.itch.io/november-pirates). Extract the zip file and run the executable. diff --git a/Scenes/Levels/Components/Ship.cs b/Scenes/Levels/Components/Ship.cs index 12a7cfd..648144f 100644 --- a/Scenes/Levels/Components/Ship.cs +++ b/Scenes/Levels/Components/Ship.cs @@ -50,6 +50,7 @@ public Ship(HullType hull, BoatColor color, Team team) internal float Currency; internal Port? TargetPort; internal List SailingRoute; + internal int Wood; public Task> NavTask { get; set; } } diff --git a/Scenes/Levels/Systems/PickupSystem.cs b/Scenes/Levels/Systems/PickupSystem.cs index 4ee0965..7b89b5e 100644 --- a/Scenes/Levels/Systems/PickupSystem.cs +++ b/Scenes/Levels/Systems/PickupSystem.cs @@ -4,7 +4,6 @@ using NovemberPirates.Extensions; using NovemberPirates.Scenes.Levels.Components; using NovemberPirates.Systems; -using NovemberPirates.Utilities.Data; using Raylib_CsLo; using System.Numerics; @@ -17,7 +16,11 @@ internal override void Update(World world) var singletonEntity = world.QueryFirst(); var singleton = singletonEntity.Get(); + var player = world.QueryFirst(); + var playerSprite = player.Get(); + var crewQuery = new QueryDescription().WithAll(); + var woodQuery = new QueryDescription().WithAll(); world.Query(crewQuery, (entity) => { @@ -25,6 +28,14 @@ internal override void Update(World world) var crewMember = entity.Get(); crewMember.Elapsed += Raylib.GetFrameTime(); + if (playerSprite.Position.DistanceTo(sprite.Position) < 50) + { + world.Destroy(entity); + var playerShip = player.Get(); + playerShip.Crew += 1; + world.Create().Set(new AudioEvent() { Key = Utilities.AudioKey.Yarr, Position = sprite.Position }); + } + if (crewMember.Elapsed > crewMember.Duration) { world.Destroy(entity); @@ -34,6 +45,19 @@ internal override void Update(World world) { sprite.Position += Vector2.Normalize(crewMember.Target - sprite.Position) * Raylib.GetFrameTime() * crewMember.Speed; } + }); + + world.Query(woodQuery, (entity) => + { + var sprite = entity.Get(); + + if (playerSprite.Position.DistanceTo(sprite.Position) < 50) + { + world.Destroy(entity); + var playerShip = player.Get(); + playerShip.Wood += 1; + world.Create().Set(new AudioEvent() { Key = Utilities.AudioKey.CollectWood, Position = sprite.Position }); + } }); } diff --git a/Scenes/Menus/Components/UiContainer.cs b/Scenes/Menus/Components/UiContainer.cs new file mode 100644 index 0000000..4248d9d --- /dev/null +++ b/Scenes/Menus/Components/UiContainer.cs @@ -0,0 +1,9 @@ +using Raylib_CsLo; + +namespace NovemberPirates.Scenes.Menus.Components +{ + internal class UiContainer + { + internal Rectangle Rectangle = new(); + } +} diff --git a/Scenes/Menus/MainMenu/CreditsScene.cs b/Scenes/Menus/MainMenu/CreditsScene.cs index 752be02..837253f 100644 --- a/Scenes/Menus/MainMenu/CreditsScene.cs +++ b/Scenes/Menus/MainMenu/CreditsScene.cs @@ -1,5 +1,6 @@ using NovemberPirates.Scenes.Menus.Components; using NovemberPirates.Scenes.Menus.Systems; +using Raylib_CsLo; namespace NovemberPirates.Scenes.Menus.MainMenu { @@ -8,14 +9,18 @@ internal class CreditsScene : BaseScene public CreditsScene() { Systems.Add(new MenuSystem()); + Systems.Add(new MenuMusicSystem()); - World.Create(new UiTitle { Text = @"Credits", Order = 1 }); - World.Create(new UiTitle { Text = @"Nhawdge - Code", Order = 2 }); - World.Create(new UiTitle { Text = @"Kaitlyn Schmidt - Game Design", Order = 3 }); - World.Create(new UiTitle { Text = @"Game Design and Project Management?", Order = 4 }); - World.Create(new UiTitle { Text = @"Barun Sinha - Sounds", Order = 5 }); - World.Create(new UiTitle { Text = @"UnicornGirlie - Art ", Order = 6 }); - World.Create(new UiTitle { Text = @"Kenney.nl - Pirate Asset Pack", Order = 7 }); + var index = 5; + World.Create(new UiContainer { Rectangle = new Rectangle() }); + + World.Create(new UiTitle { Text = @"Credits", Order = index++ }); + World.Create(new UiTitle { Text = @"Nhawdge - Code", Order = index++ }); + World.Create(new UiTitle { Text = @"Kaitlyn Schmidt - Game Design", Order = index++ }); + World.Create(new UiTitle { Text = @"Barun Sinha - Sounds", Order = index++ }); + World.Create(new UiTitle { Text = @"UnicornGirlie - Title Art ", Order = index++ }); + World.Create(new UiTitle { Text = @"CFHM - Yarrs", Order = index++ }); + World.Create(new UiTitle { Text = @"Kenney.nl - Pirate Asset Pack", Order = index++ }); World.Create(new UiButton { @@ -24,7 +29,7 @@ public CreditsScene() { NovemberPiratesEngine.Instance.ActiveScene = new MainMenuScene(); }, - Order = 9 + Order = index++ }); } } diff --git a/Scenes/Menus/MainMenu/HowToPlayScene.cs b/Scenes/Menus/MainMenu/HowToPlayScene.cs index fcfef92..a55651b 100644 --- a/Scenes/Menus/MainMenu/HowToPlayScene.cs +++ b/Scenes/Menus/MainMenu/HowToPlayScene.cs @@ -2,6 +2,7 @@ using Arch.Core.Extensions; using NovemberPirates.Scenes.Menus.Components; using NovemberPirates.Scenes.Menus.Systems; +using Raylib_CsLo; namespace NovemberPirates.Scenes.Menus.MainMenu { @@ -10,13 +11,18 @@ internal class HowToPlayScene : BaseScene public HowToPlayScene() { Systems.Add(new MenuSystem()); + Systems.Add(new MenuMusicSystem()); + + var index = 5; + + World.Create(new UiContainer { Rectangle = new Rectangle() }); var instructions = World.Create(); - instructions.Set(new UiTitle { Text = @"WASD to move Q/E or Arrow keys to shoot", Order = 1 }); + instructions.Set(new UiTitle { Text = @"WASD to move Q/E or Arrow keys to shoot", Order = index++ }); var instructions2 = World.Create(); - instructions2.Set(new UiTitle { Text = @"f3 to change the wind", Order = 2 }); + instructions2.Set(new UiTitle { Text = @"f3 to change the wind", Order = index++ }); var instructions3 = World.Create(); - instructions3.Set(new UiTitle { Text = @"F2 for the debugger I'm proud of", Order = 3 }); + instructions3.Set(new UiTitle { Text = @"F2 for the debugger I'm proud of", Order = index++ }); World.Create(new UiButton { @@ -25,7 +31,7 @@ public HowToPlayScene() { NovemberPiratesEngine.Instance.ActiveScene = new MainMenuScene(); }, - Order = 5 + Order = index++ }); } diff --git a/Scenes/Menus/MainMenu/PauseScene.cs b/Scenes/Menus/MainMenu/PauseScene.cs index 31df9a2..5c374a9 100644 --- a/Scenes/Menus/MainMenu/PauseScene.cs +++ b/Scenes/Menus/MainMenu/PauseScene.cs @@ -8,6 +8,7 @@ internal class PauseScene : BaseScene public PauseScene(BaseScene lastScene) { Systems.Add(new MenuSystem()); + Systems.Add(new MenuMusicSystem()); World.Create(new UiButton { diff --git a/Scenes/Menus/MainMenu/SettingsScene.cs b/Scenes/Menus/MainMenu/SettingsScene.cs index 6ead169..65a8703 100644 --- a/Scenes/Menus/MainMenu/SettingsScene.cs +++ b/Scenes/Menus/MainMenu/SettingsScene.cs @@ -1,12 +1,38 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using System.Threading.Tasks; +using Arch.Core.Extensions; +using NovemberPirates.Scenes.Menus.Components; +using NovemberPirates.Scenes.Menus.Systems; +using Raylib_CsLo; namespace NovemberPirates.Scenes.Menus.MainMenu { - internal class SettingsScene + internal class SettingsScene : BaseScene { + public SettingsScene() + { + Systems.Add(new MenuSystem()); + Systems.Add(new MenuMusicSystem()); + + var index = 5; + + World.Create(new UiContainer { Rectangle = new Rectangle() }); + + var instructions = World.Create(); + instructions.Set(new UiTitle { Text = @"WASD to move Q/E or Arrow keys to shoot", Order = index++ }); + var instructions2 = World.Create(); + instructions2.Set(new UiTitle { Text = @"f3 to change the wind", Order = index++ }); + var instructions3 = World.Create(); + instructions3.Set(new UiTitle { Text = @"F2 for the debugger I'm proud of", Order = index++ }); + + World.Create(new UiButton + { + Text = "Back", + Action = () => + { + NovemberPiratesEngine.Instance.ActiveScene = new MainMenuScene(); + }, + Order = index++ + }); + } + } } diff --git a/Scenes/Menus/Systems/MenuSystem.cs b/Scenes/Menus/Systems/MenuSystem.cs index 9e4a10d..79f7151 100644 --- a/Scenes/Menus/Systems/MenuSystem.cs +++ b/Scenes/Menus/Systems/MenuSystem.cs @@ -21,11 +21,27 @@ internal override void UpdateNoCamera(World world) new Rectangle(0, 0, Raylib.GetScreenWidth(), Raylib.GetScreenHeight()), Vector2.Zero, 0f, Raylib.WHITE); var query = new QueryDescription().WithAny(); + var uiElementCount = world.CountEntities(in query); var centerPoint = new Vector2(Raylib.GetScreenWidth() / 2, Raylib.GetScreenHeight() / 2); - var dummyrect = new Rectangle(centerPoint.X - 200, centerPoint.Y - 300, 400, 500); - //RayGui.GuiDummyRec(dummyrect, ""); + var placementContainer = new Rectangle(centerPoint.X - 300, centerPoint.Y - 300, 600, 500); + + var container = world.QueryFirstOrNull(); + if (container.HasValue) + { + var uiContainer = container.Value.Get(); + + //Raylib.DrawRectangleRec(container.Rectangle, Color.BLACK); + RayGui.GuiDummyRec(uiContainer.Rectangle with + { + X = placementContainer.x, + y = placementContainer.y, + width = placementContainer.width, + height = 55 * uiElementCount + }, ""); + } + var index = 0; //RayGui.GuiSetFont(CreditsFont); @@ -52,7 +68,13 @@ internal override void UpdateNoCamera(World world) if (entity.Has()) { var button = entity.Get(); - var rect = dummyrect with { x = dummyrect.x + 100, y = dummyrect.y + (60 * button.Order), width = 200, height = 50 }; + var rect = placementContainer with + { + x = placementContainer.x + placementContainer.width / 2 - 200 / 2, + y = placementContainer.y + (60 * button.Order), + width = 200, + height = 50 + }; if (RayGui.GuiButton(rect, button.Text)) { diff --git a/Utilities/AudioManager.cs b/Utilities/AudioManager.cs index 0b8a03d..059f9e2 100644 --- a/Utilities/AudioManager.cs +++ b/Utilities/AudioManager.cs @@ -10,7 +10,6 @@ private AudioManager() { } public Dictionary AudioStore = new(); public Dictionary MusicStore = new(); - internal void LoadAllAudio() { AudioStore.Add(AudioKey.CannonFire, new[] { @@ -63,6 +62,15 @@ internal void LoadAllAudio() Raylib.LoadSound("Assets/Audio/sfx_WindinSail.ogg"), }); + AudioStore.Add(AudioKey.Yarr, new[] + { + Raylib.LoadSound("Assets/Audio/yarrs01.wav"), + Raylib.LoadSound("Assets/Audio/yarrs02.wav"), + Raylib.LoadSound("Assets/Audio/yarrs03.wav"), + }); + + // M U S I C + MusicStore.Add(AudioKey.Charge, Raylib.LoadMusicStream("Assets/Audio/Charge.wav")); MusicStore.Add(AudioKey.Drifting, Raylib.LoadMusicStream("Assets/Audio/Drifting.wav")); MusicStore.Add(AudioKey.TheBleedingOcean, Raylib.LoadMusicStream("Assets/Audio/The-Bleeding-Ocean.wav")); @@ -118,5 +126,6 @@ internal enum AudioKey Drifting, TheWarriorsOfTheWater, TheBleedingOcean, + Yarr, } } diff --git a/Utilities/SettingsManager.cs b/Utilities/SettingsManager.cs new file mode 100644 index 0000000..e6bfb9d --- /dev/null +++ b/Utilities/SettingsManager.cs @@ -0,0 +1,46 @@ +using System.Security.Cryptography.X509Certificates; +using System.Text.Json; + +namespace NovemberPirates.Utilities +{ + internal class SettingsManager + { + private SettingsManager() { } + + internal static SettingsManager Instance = new(); + + internal Dictionary Settings = new(); + + internal void LoadSettings() + { + if (File.Exists("settings.json")) + { + try + { + var settings = File.ReadAllText("settings.json"); + Settings = JsonSerializer.Deserialize>(settings); + } + catch (Exception ex) + { + Console.WriteLine($"Error: {ex.Message}"); + } + } + else + { + Settings.Add(SettingKeys.MainVolume, 0.5f); + Settings.Add(SettingKeys.MusicVolume, 0.5f); + Settings.Add(SettingKeys.SfxVolume, 0.5f); + + File.WriteAllText("settings.json", JsonSerializer.Serialize(Settings)); + } + } + + internal enum SettingKeys + { + MainVolume, + MusicVolume, + SfxVolume, + Language + } + } +}