Imported newly created Nuclex.Support library which contains various supporting classes not related to a specific topic
git-svn-id: file:///srv/devel/repo-conversion/nusu@1 d2e56fa2-650e-0410-a79f-9358c0239efd
This commit is contained in:
commit
ce8df64be5
10 changed files with 1043 additions and 0 deletions
66
Source/Serialization/BinarySerializer.Test.cs
Normal file
66
Source/Serialization/BinarySerializer.Test.cs
Normal file
|
@ -0,0 +1,66 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
|
||||
#if UNITTEST
|
||||
|
||||
using NUnit.Framework;
|
||||
|
||||
namespace Nuclex.Support.Serialization {
|
||||
|
||||
/// <summary>Ensures that the binary serializer is working correctly</summary>
|
||||
[TestFixture]
|
||||
public class BinarySerializerTest {
|
||||
|
||||
private class TestSerializable : IBinarySerializable {
|
||||
public void Load(BinaryReader reader) { this.Dummy = reader.ReadInt32(); }
|
||||
public void Save(BinaryWriter writer) { writer.Write(this.Dummy); }
|
||||
public int Dummy;
|
||||
}
|
||||
|
||||
/// <summary>Prepares some test data for the units test methods</summary>
|
||||
[TestFixtureSetUp]
|
||||
public void Setup() {
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Ensures that the ring buffer blocks write attempts that would exceed its capacity
|
||||
/// </summary>
|
||||
[Test]
|
||||
public void TestTooLargeChunk() {
|
||||
MemoryStream buffer = new MemoryStream();
|
||||
|
||||
// Fill and save
|
||||
{
|
||||
List<TestSerializable> serializables = new List<TestSerializable>();
|
||||
|
||||
serializables.Add(new TestSerializable());
|
||||
serializables.Add(new TestSerializable());
|
||||
serializables[0].Dummy = 123;
|
||||
serializables[1].Dummy = 456;
|
||||
|
||||
BinarySerializer<TestSerializable>.SaveCollection(
|
||||
serializables, new BinaryWriter(buffer)
|
||||
);
|
||||
buffer.Position = 0;
|
||||
}
|
||||
|
||||
// Load and validate
|
||||
{
|
||||
List<TestSerializable> serializables = new List<TestSerializable>();
|
||||
|
||||
BinarySerializer<TestSerializable>.LoadCollection(
|
||||
serializables, new BinaryReader(buffer)
|
||||
);
|
||||
|
||||
Assert.AreEqual(2, serializables.Count);
|
||||
Assert.AreEqual(123, serializables[0].Dummy);
|
||||
Assert.AreEqual(456, serializables[1].Dummy);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} // namespace Nuclex.Support.Serialization
|
||||
|
||||
#endif // UNITTEST
|
71
Source/Serialization/BinarySerializer.cs
Normal file
71
Source/Serialization/BinarySerializer.cs
Normal file
|
@ -0,0 +1,71 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Reflection;
|
||||
|
||||
using Nuclex.Support.Serialization;
|
||||
|
||||
namespace Nuclex.Support.Serialization {
|
||||
|
||||
/// <summary>Utility class for serialization objects into binary data</summary>
|
||||
/// <typeparam name="BinarySerializableType">Data type to be serialized</typeparam>
|
||||
public static class BinarySerializer<BinarySerializableType>
|
||||
where BinarySerializableType : IBinarySerializable {
|
||||
|
||||
/// <summary>Serializes a collection of binary serializable objects</summary>
|
||||
/// <param name="collection">Collection to be serialized</param>
|
||||
/// <param name="writer">BinaryWriter to serialize the collection into</param>
|
||||
public static void SaveCollection(
|
||||
ICollection<BinarySerializableType> collection, BinaryWriter writer
|
||||
) {
|
||||
|
||||
// Save the file format version so the loading routine can detect
|
||||
// which version of the file format has to be loaded
|
||||
writer.Write((int)1);
|
||||
|
||||
// Serialize all the blueprints in the collection
|
||||
writer.Write((int)collection.Count);
|
||||
foreach(BinarySerializableType item in collection) {
|
||||
|
||||
// Save the type name of the object so we can recreate it later
|
||||
writer.Write(item.GetType().AssemblyQualifiedName);
|
||||
|
||||
// Let the object save its own data
|
||||
((IBinarySerializable)item).Save(writer);
|
||||
|
||||
} // foreach
|
||||
|
||||
}
|
||||
|
||||
/// <summary>Loads a collection from its serialized representation</summary>
|
||||
/// <param name="collection">Collection to be deserialized into</param>
|
||||
/// <param name="reader">Reader to use for reading the collection</param>
|
||||
public static void LoadCollection(
|
||||
ICollection<BinarySerializableType> collection, BinaryReader reader
|
||||
) {
|
||||
|
||||
// Read and verify the version of the file format this was saved in
|
||||
int version = reader.ReadInt32();
|
||||
if(version > 1)
|
||||
throw new InvalidOperationException("File format is too new");
|
||||
|
||||
// Read all the serialized blueprints
|
||||
int count = reader.ReadInt32();
|
||||
for(int index = 0; index < count; ++index) {
|
||||
|
||||
// Try to create an instance from the serialized type name
|
||||
BinarySerializableType item = (BinarySerializableType)Activator.CreateInstance(
|
||||
Type.GetType(reader.ReadString())
|
||||
);
|
||||
|
||||
// Let the blueprint load its own data and add it to the collection
|
||||
((IBinarySerializable)item).Load(reader);
|
||||
collection.Add(item);
|
||||
|
||||
} // for
|
||||
|
||||
}
|
||||
|
||||
} // class BinarySerializer
|
||||
|
||||
} // namespace Nuclex.Support.Serialization
|
27
Source/Serialization/IBinarySerializable.cs
Normal file
27
Source/Serialization/IBinarySerializable.cs
Normal file
|
@ -0,0 +1,27 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
|
||||
namespace Nuclex.Support.Serialization {
|
||||
|
||||
/// <summary>Interface for objects able to serialize themselfes into a binary format</summary>
|
||||
/// <remarks>
|
||||
/// Sometimes, the limitations of XML serialization are too strict, especially
|
||||
/// in the context of a game where you might need to serialize larger chunks of
|
||||
/// binary data or in cases where you do not wish to expose a default constructor
|
||||
/// in your classes. This interface defines two simple methods that can be
|
||||
/// used to load and save an object's state in a simple manner.
|
||||
/// </remarks>
|
||||
public interface IBinarySerializable {
|
||||
|
||||
/// <summary>Loads the object's state from its serialized representation</summary>
|
||||
/// <param name="reader">Reader to use for reading the object's state</param>
|
||||
void Load(BinaryReader reader);
|
||||
|
||||
/// <summary>Save the object's state into a serialized representation</summary>
|
||||
/// <param name="writer">Writer to use for writing the object's state</param>
|
||||
void Save(BinaryWriter writer);
|
||||
|
||||
}
|
||||
|
||||
} // namespace Nuclex.Support.Serialization
|
Loading…
Add table
Add a link
Reference in a new issue