diff --git a/PDGServer_WPF/App.xaml b/PDGServer_WPF/App.xaml
index 7124177..f4328e6 100644
--- a/PDGServer_WPF/App.xaml
+++ b/PDGServer_WPF/App.xaml
@@ -2,5 +2,5 @@
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:RBG_Server"
- StartupUri="MainWindow.xaml">
+ StartupUri="ConnectionPage.xaml">
diff --git a/PDGServer_WPF/App.xaml.cs b/PDGServer_WPF/App.xaml.cs
index 8d26332..3ad354f 100644
--- a/PDGServer_WPF/App.xaml.cs
+++ b/PDGServer_WPF/App.xaml.cs
@@ -10,6 +10,7 @@ using System.Threading.Tasks;
using System.Windows;
using System.Windows.Media;
using System.Windows.Media.Imaging;
+using System.Windows.Navigation;
namespace RBG_Server
{
@@ -31,6 +32,13 @@ namespace RBG_Server
public const string MIP_HIGH = "_mip_high";
public const string MIP_RAW = "_mip_raw";
+ protected override void OnStartup(StartupEventArgs e)
+ {
+ base.OnStartup(e);
+ Context = this;
+ GameCommunicationHandler = new CommunicationHandler();
+ }
+
///
/// Loads the specified files from disk, creating mip maps as appropriate
///
@@ -121,7 +129,8 @@ namespace RBG_Server
BitmapImage bitmapImage = new();
bitmapImage.BeginInit();
bitmapImage.StreamSource = source;
- bitmapImage.CacheOption = BitmapCacheOption.None;
+ bitmapImage.CreateOptions = BitmapCreateOptions.IgnoreColorProfile | BitmapCreateOptions.PreservePixelFormat;
+ bitmapImage.CacheOption = BitmapCacheOption.Default;
bitmapImage.EndInit();
int height = bitmapImage.PixelHeight;
int width = bitmapImage.PixelWidth;
@@ -194,15 +203,28 @@ namespace RBG_Server
GameCommunicationHandler.ImageCollection.Remove(GameCommunicationHandler.BoardName, out CachedByteArray val);
val.Dispose();
}
- GameCommunicationHandler.BoardName = path;
+ GameCommunicationHandler.BoardName = Path.GetFileNameWithoutExtension(path);
}
- GameCommunicationHandler.ImageList.Add(path);
+ GameCommunicationHandler.ImageList.Add(Path.GetFileNameWithoutExtension(path));
}
}
- MemoryStream ScaleImage(BitmapSource source, double scaleRate)
+ static MemoryStream ScaleImage(BitmapSource source, double scaleRate)
{
- TransformedBitmap modified = new(source, new ScaleTransform(source.PixelWidth * scaleRate, source.PixelHeight * scaleRate));
+ TransformedBitmap modified = new();
+ try
+ {
+ ScaleTransform transform = new ScaleTransform(scaleRate, scaleRate);
+ modified.BeginInit();
+ modified.Source = source;
+ modified.Transform = transform;
+ modified.EndInit();
+ //modified = new(source, );
+ }
+ catch (Exception ex)
+ {
+ int op = 0;
+ }
PngBitmapEncoder encoder = new();
encoder.Frames.Add(BitmapFrame.Create(modified));
MemoryStream ms = new();
@@ -210,7 +232,7 @@ namespace RBG_Server
return ms;
}
- MemoryStream ScaleAnimatedImage(BitmapFrame[] frames, double scaleRate)
+ static MemoryStream ScaleAnimatedImage(BitmapFrame[] frames, double scaleRate)
{
PngBitmapEncoder encoder = new();
foreach (BitmapFrame frame in frames)
diff --git a/PDGServer_WPF/ConnectionPage.xaml b/PDGServer_WPF/ConnectionPage.xaml
index e25e0ca..8cdcc8b 100644
--- a/PDGServer_WPF/ConnectionPage.xaml
+++ b/PDGServer_WPF/ConnectionPage.xaml
@@ -1,19 +1,17 @@
-
+ xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
+ xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
+ xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
+ mc:Ignorable="d"
+ Title="PDG Server" Height="768" Width="1024" Background="#FF4B4B4B">
-
-
+
+
-
+
@@ -50,7 +48,7 @@
-
+
@@ -70,4 +68,4 @@
-
+
diff --git a/PDGServer_WPF/ConnectionPage.xaml.cs b/PDGServer_WPF/ConnectionPage.xaml.cs
index f337a10..a55ef65 100644
--- a/PDGServer_WPF/ConnectionPage.xaml.cs
+++ b/PDGServer_WPF/ConnectionPage.xaml.cs
@@ -24,7 +24,7 @@ namespace RBG_Server_WPF
///
/// Interaction logic for ConnectionPage.xaml
///
- public partial class ConnectionPage : Page
+ public partial class ConnectionPage : Window
{
public ConnectionPage()
{
@@ -260,7 +260,9 @@ namespace RBG_Server_WPF
if (ofd.ShowDialog() == true)
{
ImageSourceTextBox.Text = ofd.FileName;
- UpdateImage().Start();
+
+ Task.Run(() => UpdateImage(ofd.FileName));
+
}
}
///
@@ -270,34 +272,38 @@ namespace RBG_Server_WPF
///
private void ImageSourceTextBox_LostFocus(object sender, RoutedEventArgs e)
{
- UpdateImage().Start();
+ //UpdateImage().Start();
}
- private Task UpdateImage()
+ private void UpdateImage(string sourceFile)
{
try
{
CommunicationHandler host = App.Context.GameCommunicationHandler;
- using FileStream fs = File.OpenRead(ImageSourceTextBox.Text);
+ using FileStream fs = File.OpenRead(sourceFile);
using MemoryStream ms = new();
fs.CopyTo(ms);
// Calc mips
ms.Position = 0;
- App.Context.LoadStream(ms, Name, false);
+ App.Context.LoadStream(ms, sourceFile, false);
ms.Position = 0;
- BitmapImage gameBoardImage = new();
- gameBoardImage.BeginInit();
- gameBoardImage.StreamSource = ms;
- gameBoardImage.EndInit();
- PreviewImage.Source = gameBoardImage;
- RedrawGrid();
+
+ this.Dispatcher.Invoke(() => {
+ BitmapImage gameBoardImage = new();
+ gameBoardImage.BeginInit();
+ gameBoardImage.StreamSource = ms;
+ gameBoardImage.CacheOption = BitmapCacheOption.OnLoad;
+ gameBoardImage.EndInit();
+ PreviewImage.Source = gameBoardImage;
+ RedrawGrid();
+ }, System.Windows.Threading.DispatcherPriority.Render);
+
}
catch (Exception e)
{
Console.WriteLine(e);
}
- return Task.CompletedTask;
}
///
@@ -371,10 +377,44 @@ namespace RBG_Server_WPF
}
}
}
+ private void GridVisibilityToggleButton_Click(object sender, RoutedEventArgs e)
+ {
+ PreviewImageOverlay.Visibility = PreviewImageOverlay.Visibility == Visibility.Visible ? Visibility.Collapsed : Visibility.Visible;
+ }
+
+ ///
+ /// Performs the logic required to start the server
+ ///
+ ///
+ ///
+ private void StartServerButton_Click(object sender, RoutedEventArgs e)
+ {
+ CommunicationHandler host = App.Context.GameCommunicationHandler;
+ host.InitialiseServer((int)NumberOfRows.Value, (int)NumberOfColumns.Value, (int)ZoomBoxStartRow.Value, (int)ZoomBoxStartColumn.Value, (int)ZoomBoxSpan.Value, (int)ZoomBoxSpan.Value, (int)StartingRow.Value, (int)StartingColumn.Value);
+ }
+
#endregion
+ private void Sliders_ValueChanged(object sender, RoutedPropertyChangedEventArgs e)
+ {
+ }
+
+ private void NumberOfRows_ValueChanged(object sender, RoutedPropertyChangedEventArgs e)
+ {
+
+ }
+
+ private void DrawRandomizedPlayers_Click(object sender, RoutedEventArgs e)
+ {
+
+ }
+
+ private void NumberOfColumns_ValueChanged(object sender, RoutedPropertyChangedEventArgs e)
+ {
+
+ }
}
}
diff --git a/PDGServer_WPF/MainWindow.xaml b/PDGServer_WPF/MainWindow.xaml
index 2f568ef..be94ddc 100644
--- a/PDGServer_WPF/MainWindow.xaml
+++ b/PDGServer_WPF/MainWindow.xaml
@@ -11,36 +11,6 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
diff --git a/PDGServer_WPF/MainWindow.xaml.cs b/PDGServer_WPF/MainWindow.xaml.cs
index 7c274ae..60172ff 100644
--- a/PDGServer_WPF/MainWindow.xaml.cs
+++ b/PDGServer_WPF/MainWindow.xaml.cs
@@ -35,131 +35,51 @@ namespace RBG_Server.WPF
InitializeComponent();
}
- ///
- /// Browse for game board file button
- ///
- ///
- ///
- private void BrowseButton_Click(object sender, RoutedEventArgs e)
- {
- OpenFileDialog ofd = new();
- ofd.Filter = "Image Files|*.png;*.jpg";
- if (ofd.ShowDialog() == true)
- {
- ImageSourceTextBox.Text = ofd.FileName;
- UpdateImage();
- }
- }
-
- ///
- /// Update the image when the text box looses focus
- ///
- ///
- ///
- private void ImageSourceTextBox_LostFocus(object sender, RoutedEventArgs e)
- {
- UpdateImage();
- }
-
- private void UpdateImage()
- {
- try
- {
- using FileStream fs = File.OpenRead(ImageSourceTextBox.Text);
- using MemoryStream ms = new();
- fs.CopyTo(ms); // Load into memory, so the server can also utilise the stream
- gameBoard = ms.ToArray();
-
- BitmapImage gameBoardImage = new();
- gameBoardImage.BeginInit();
- gameBoardImage.StreamSource = new MemoryStream(gameBoard, false);
- //gameBoardImage.CacheOption = BitmapCacheOption.OnLoad; // Must preload the image into memory, before it is unloaded
- gameBoardImage.EndInit();
- PreviewImage.Source = gameBoardImage;
- RedrawGrid();
- }
- catch (Exception e)
- {
- Console.WriteLine(e);
- }
- }
- ///
- /// Creates and starts the game server
- ///
- ///
- ///
- private void StartServerButton_Click(object sender, RoutedEventArgs e)
- {
- gameServer = new((byte)StartingRow.Value, (byte)StartingColumn.Value, (byte)NumberOfRows.Value, (byte)NumberOfColumns.Value, (byte)ZoomBoxStartRow.Value, (byte)ZoomBoxStartColumn.Value, (byte)ZoomBoxSpan.Value, (byte)ZoomBoxSpan.Value, gameBoard);
- }
-
-
- private void NumberOfRows_ValueChanged(object sender, RoutedPropertyChangedEventArgs e)
- {
- if (IsInitialized)
- {
- StartingRow.Maximum = NumberOfRows.Value;
- ZoomBoxStartRow.Maximum = NumberOfRows.Value;
- ZoomBoxSpan.Maximum = Math.Min(NumberOfRows.Value - ZoomBoxStartRow.Value, NumberOfColumns.Value - ZoomBoxStartColumn.Value);
- RedrawGrid();
- }
- }
-
- private void NumberOfColumns_ValueChanged(object sender, RoutedPropertyChangedEventArgs e)
- {
- if (IsInitialized)
- {
- StartingColumn.Maximum = NumberOfColumns.Value;
- ZoomBoxStartColumn.Maximum = NumberOfColumns.Value;
- ZoomBoxSpan.Maximum = Math.Min(NumberOfRows.Value - ZoomBoxStartRow.Value, NumberOfColumns.Value - ZoomBoxStartColumn.Value);
- RedrawGrid();
- }
- }
///
/// Draws the overlay grid, clearing existing elements if necessary
///
- private void RedrawGrid()
- {
+ //private void RedrawGrid()
+ //{
- PreviewImageOverlay.RowDefinitions.Clear();
- PreviewImageOverlay.ColumnDefinitions.Clear();
- PreviewImageOverlay.Children.Clear();
- for (int i = 0; i < NumberOfColumns.Value; i++)
- {
- PreviewImageOverlay.ColumnDefinitions.Add(new ColumnDefinition());
- }
- for (int i = 0; i < NumberOfRows.Value; i++)
- {
- PreviewImageOverlay.RowDefinitions.Add(new RowDefinition());
- }
- // Draw the overlay
- Rectangle overlay = new();
- overlay.Fill = new SolidColorBrush(Color.FromArgb(128, 0, 128, 255));
- _ = PreviewImageOverlay.Children.Add(overlay);
- Grid.SetRow(overlay, (int)ZoomBoxStartRow.Value);
- Grid.SetColumn(overlay, (int)ZoomBoxStartColumn.Value);
- Grid.SetRowSpan(overlay, (int)ZoomBoxSpan.Value);
- Grid.SetColumnSpan(overlay, (int)ZoomBoxSpan.Value);
- // Draw the starting position
- overlay = new();
- overlay.Fill = new SolidColorBrush(Color.FromArgb(64, 0, 255, 128));
- _ = PreviewImageOverlay.Children.Add(overlay);
- Grid.SetRow(overlay, (int)StartingRow.Value);
- Grid.SetColumn(overlay, (int)StartingColumn.Value);
- // Draw grids onto the preview image
- for (int v = 0; v < PreviewImageOverlay.RowDefinitions.Count; v++)
- {
- for (int u = 0; u < PreviewImageOverlay.ColumnDefinitions.Count; u++)
- {
- Border border = new();
- border.BorderBrush = borderBrush;
- border.BorderThickness = new Thickness(2);
- _ = PreviewImageOverlay.Children.Add(border);
- Grid.SetRow(border, v);
- Grid.SetColumn(border, u);
- }
- }
- }
+ // PreviewImageOverlay.RowDefinitions.Clear();
+ // PreviewImageOverlay.ColumnDefinitions.Clear();
+ // PreviewImageOverlay.Children.Clear();
+ // for (int i = 0; i < NumberOfColumns.Value; i++)
+ // {
+ // PreviewImageOverlay.ColumnDefinitions.Add(new ColumnDefinition());
+ // }
+ // for (int i = 0; i < NumberOfRows.Value; i++)
+ // {
+ // PreviewImageOverlay.RowDefinitions.Add(new RowDefinition());
+ // }
+ // // Draw the overlay
+ // Rectangle overlay = new();
+ // overlay.Fill = new SolidColorBrush(Color.FromArgb(128, 0, 128, 255));
+ // _ = PreviewImageOverlay.Children.Add(overlay);
+ // Grid.SetRow(overlay, (int)ZoomBoxStartRow.Value);
+ // Grid.SetColumn(overlay, (int)ZoomBoxStartColumn.Value);
+ // Grid.SetRowSpan(overlay, (int)ZoomBoxSpan.Value);
+ // Grid.SetColumnSpan(overlay, (int)ZoomBoxSpan.Value);
+ // // Draw the starting position
+ // overlay = new();
+ // overlay.Fill = new SolidColorBrush(Color.FromArgb(64, 0, 255, 128));
+ // _ = PreviewImageOverlay.Children.Add(overlay);
+ // Grid.SetRow(overlay, (int)StartingRow.Value);
+ // Grid.SetColumn(overlay, (int)StartingColumn.Value);
+ // // Draw grids onto the preview image
+ // for (int v = 0; v < PreviewImageOverlay.RowDefinitions.Count; v++)
+ // {
+ // for (int u = 0; u < PreviewImageOverlay.ColumnDefinitions.Count; u++)
+ // {
+ // Border border = new();
+ // border.BorderBrush = borderBrush;
+ // border.BorderThickness = new Thickness(2);
+ // _ = PreviewImageOverlay.Children.Add(border);
+ // Grid.SetRow(border, v);
+ // Grid.SetColumn(border, u);
+ // }
+ // }
+ //}
///
/// Generates the game board overlay grid
@@ -246,182 +166,7 @@ namespace RBG_Server.WPF
{
//throw new NotImplementedException();
}
- }
-
- private void Sliders_ValueChanged(object sender, RoutedPropertyChangedEventArgs e)
- {
- if (IsInitialized)
- {
- RedrawGrid();
- }
- }
-
- private void GridVisibilityToggleButton_Click(object sender, RoutedEventArgs e)
- {
- PreviewImageOverlay.Visibility = PreviewImageOverlay.Visibility == Visibility.Visible ? Visibility.Collapsed : Visibility.Visible;
- }
-
- private static readonly string[] sprites = new string[]
- {
- "01.png",
- "02.png",
- "03.png",
- "04.png",
- };
- private void DrawRandomizedPlayers_Click(object sender, RoutedEventArgs e)
- {
- List randPlayers = new();
- Random rand = new();
- int count = rand.Next(1, 10);
- for (int i = 0; i < count; i++)
- {
- // Create a new player at a random location
- Player p = new("Player " + i, rand.Next(0, PreviewImageOverlay.RowDefinitions.Count), rand.Next(PreviewImageOverlay.ColumnDefinitions.Count));
- // Load the sprite
- string[] keys = new string[loadedSprites.Count];
- loadedSprites.Keys.CopyTo(keys, 0);
- string key = keys[rand.Next(keys.Length)];
- if (key.ToLower().EndsWith(".gif"))
- {
- try
- {
- AnimatedBitmapImage animatedBitmap = new(new MemoryStream(loadedSprites[key], false), p.PlayerSprite, Application.Current.Dispatcher);
- }
- catch
- {
- BitmapSource pSprite;
- {
- // Scope & create the base data for pSprite
- BitmapImage src = new();
- src.BeginInit();
-
- src.StreamSource = new MemoryStream(loadedSprites[key],false);
- src.EndInit();
- pSprite = src;
- }
- // Recolour:
- if (rand.Next(1, 4) == 1)
- {
- pSprite = ImageProcessing.UpdatePixelColours(pSprite, 0.0, 0.0, 1.0);
- }
- p.PlayerSprite.Source = pSprite;
-
- }
- }
- else
- {
- BitmapSource pSprite;
- {
- // Scope & create the base data for pSprite
- BitmapImage src = new();
- src.BeginInit();
- src.StreamSource = new MemoryStream(loadedSprites[key], false);
- src.EndInit();
- pSprite = src;
- }
- // Recolour:
- if (rand.Next(1, 4) == 1)
- {
- pSprite = ImageProcessing.UpdatePixelColours(pSprite, 0.0, 0.0, 1.0);
- }
- p.PlayerSprite.Source = pSprite;
- }
-
- randPlayers.Add(p);
- }
-
- GenerateGameBoard(randPlayers);
- }
-
- ConcurrentDictionary loadedSprites = new();
- Task loadingFiles;
-
- private void GameSpritesBrowser_Click(object sender, RoutedEventArgs e)
- {
- OpenFileDialog ofd = new();
- ofd.Filter = "Image Files|*.png;*.jpg;*.gif";
- ofd.Multiselect = true;
- if (ofd.ShowDialog() == true)
- {
- string[] resultFiles = ofd.FileNames;
- loadedSprites.Clear();
- // Run the following work in a separate thread
- loadingFiles = Task.Run(() =>
- {
- // Continue in parallel
- _ = Parallel.ForEach(resultFiles, (file) =>
- {
- MemoryStream ms = new();
- using FileStream fs = File.OpenRead(file);
-
- if (new FileInfo(file).Length > 512e6) // greater than 512 kB; resize the sprite to something more reasonable
- {
- BitmapImage gameBoardImage = new();
- gameBoardImage.BeginInit();
- gameBoardImage.StreamSource = fs;
- gameBoardImage.CacheOption = BitmapCacheOption.Default;
- gameBoardImage.EndInit();
- double vRate = 128 / (double)gameBoardImage.PixelHeight; // Resize so the largest dimension is 128 px
- double hRate = 128 / (double)gameBoardImage.PixelWidth;
- TransformedBitmap modified = new(gameBoardImage, new ScaleTransform(gameBoardImage.PixelWidth * Math.Min(vRate, hRate), gameBoardImage.PixelHeight * Math.Min(vRate, hRate)));
- PngBitmapEncoder encoder = new();
- encoder.Frames.Add(BitmapFrame.Create(modified));
- encoder.Save(ms);
- }
- else
- {
- fs.CopyTo(ms);
- }
- _ = loadedSprites.TryAdd(file, ms.ToArray());
- });
- // Invoke the dispatcher to add all of the sprites to the loaded sprites list
- _ = Application.Current.Dispatcher.BeginInvoke(System.Windows.Threading.DispatcherPriority.Render, new Action(() =>
- {
- LoadedSprites.Children.Clear();
- foreach (KeyValuePair item in loadedSprites)
- {
- if (item.Key.ToLower().EndsWith(".gif"))
- {
- try
- {
- Image spriteImage = new();
- // Generate the animatedBitmap
- RBG.Helpers.AnimatedBitmapImage animatedBitmap = new(new MemoryStream(item.Value, false), spriteImage, Application.Current.Dispatcher);
- _ = LoadedSprites.Children.Add(spriteImage);
- }
- catch
- {
- // On failed, use the cached data
- BitmapImage image = new();
- image.BeginInit();
- image.StreamSource = new MemoryStream(item.Value, false);
- image.EndInit();
- Image spriteImage = new()
- {
- Source = image
- };
- _ = LoadedSprites.Children.Add(spriteImage);
-
- }
- }
- else
- {
-
- BitmapImage image = new();
- image.BeginInit();
- image.StreamSource = new MemoryStream(item.Value, false);
- image.EndInit();
- Image spriteImage = new()
- {
- Source = image
- };
- _ = LoadedSprites.Children.Add(spriteImage);
- }
- }
- }));
- });
- }
- }
+ }
}
}
diff --git a/RBG_Server.Core/CachedByteArray.cs b/RBG_Server.Core/CachedByteArray.cs
index ca9090d..fbd7304 100644
--- a/RBG_Server.Core/CachedByteArray.cs
+++ b/RBG_Server.Core/CachedByteArray.cs
@@ -25,6 +25,14 @@ namespace RBG_Server
private static int memoryLimit = 1024 * 1024 * 1; // Start with a memory limit of 1 MB
private static readonly string folderPath = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), "Remote Board Game\\Cache Objects");
+
+ ///
+ /// Ensure the folder path exists
+ ///
+ static CachedByteArray()
+ {
+ Directory.CreateDirectory(folderPath);
+ }
// static properties
public static long MemoryAllocationRAM { get { return memoryAllocationRAM; } }
public static long MemoryAllocationTotal { get { return memoryAllocationTotal; } }
diff --git a/RBG_Server.Core/CommunicationHandler.cs b/RBG_Server.Core/CommunicationHandler.cs
index a8963b1..5191933 100644
--- a/RBG_Server.Core/CommunicationHandler.cs
+++ b/RBG_Server.Core/CommunicationHandler.cs
@@ -61,7 +61,7 @@ namespace RBG_Server
public int StartingRow { get;private set; }
- public void InitialiseServer()
+ public void InitialiseServer(int rowCount, int colCount, int zoomRowStart, int zoomColStart, int zoomRowSpan, int zoomColSpan, int startingRow, int startingColumn)
{
// Find the server's active (reliable) network adapter, by creating a remote connection and retrieving our IP from it:
using (Socket s = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp))
diff --git a/RBG_Server.Core/GameServer.cs b/RBG_Server.Core/GameServer.cs
index 991dd3b..f32b88b 100644
--- a/RBG_Server.Core/GameServer.cs
+++ b/RBG_Server.Core/GameServer.cs
@@ -208,7 +208,7 @@ namespace RBG_Server
{
// TODO:
// Check that the player isn't reconnecting
- Player newPlayer = new("", startRow, startColumn);
+ Player newPlayer = new("", "", Array.Empty(), startRow, startColumn);
Players.Add(newPlayer);
clients.Add(poppedClient, newPlayer);
Console.WriteLine("New player added.");