mirror of
https://gitlab.com/Syroot/Worms.git
synced 2025-04-09 19:00:06 +03:00
Added support for saving Project X schemes and libraries.
This commit is contained in:
parent
ece703f755
commit
95687b273b
@ -29,8 +29,8 @@ Formats of the second generation 2D games are mostly focused right now.
|
|||||||
| Monochrome Map | LEV | W2 | No | No |
|
| Monochrome Map | LEV | W2 | No | No |
|
||||||
| Monochrome Map | BIT | WA, WWP | No | No |
|
| Monochrome Map | BIT | WA, WWP | No | No |
|
||||||
| Palette | PAL | W2, WA, WWP | Yes | Yes |
|
| Palette | PAL | W2, WA, WWP | Yes | Yes |
|
||||||
| Project X Library | PXL | WA+PX | Yes | No |
|
| Project X Library | PXL | WA+PX | Yes | Yes |
|
||||||
| Project X Scheme | PXS | WA+PX | Yes | No |
|
| Project X Scheme | PXS | WA+PX | Yes | Yes |
|
||||||
| Replay | WAGAME | WA | No | No |
|
| Replay | WAGAME | WA | No | No |
|
||||||
| Scheme | WSC | WA, WWP | Yes | Yes |
|
| Scheme | WSC | WA, WWP | Yes | Yes |
|
||||||
| Scheme Options | OPT | W2 | Yes | Yes |
|
| Scheme Options | OPT | W2 | Yes | Yes |
|
||||||
|
@ -10,28 +10,17 @@ namespace Syroot.Worms.Test
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
internal class Program
|
internal class Program
|
||||||
{
|
{
|
||||||
// ---- CONSTANTS ----------------------------------------------------------------------------------------------
|
|
||||||
|
|
||||||
private static readonly string[] _testPaths = { @"C:\Games\Worms Armageddon 3.7.2.1" };
|
|
||||||
|
|
||||||
// ---- METHODS (PRIVATE) --------------------------------------------------------------------------------------
|
// ---- METHODS (PRIVATE) --------------------------------------------------------------------------------------
|
||||||
|
|
||||||
private static void Main(string[] args)
|
private static void Main(string[] args)
|
||||||
{
|
{
|
||||||
Scheme pxScheme = new Scheme(@"D:\Archive\Games\Worms\Worms Armageddon\3.6.31.0\PXSchemes\PacStruction.pxs");
|
Library library = new Library(@"D:\Archive\Games\Worms\Worms Armageddon\3.6.31.0\Libs\cnades.pxl");
|
||||||
|
library.Save(@"D:\Pictures\saved.pxl");
|
||||||
|
|
||||||
|
//Scheme pxScheme = new Scheme(@"D:\Archive\Games\Worms\Worms Armageddon\3.6.31.0\PXSchemes\PacStruction.pxs");
|
||||||
|
|
||||||
Console.WriteLine("Done.");
|
Console.WriteLine("Done.");
|
||||||
Console.ReadLine();
|
Console.ReadLine();
|
||||||
}
|
}
|
||||||
|
|
||||||
private static List<string> GetFiles(string wildcard)
|
|
||||||
{
|
|
||||||
List<string> files = new List<string>();
|
|
||||||
foreach (string testPath in _testPaths)
|
|
||||||
{
|
|
||||||
files.AddRange(Directory.GetFiles(testPath, wildcard, SearchOption.AllDirectories));
|
|
||||||
}
|
|
||||||
return files;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="Archive"/> class.
|
/// Represents a collection of tests for the <see cref="Archive"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("Archive")]
|
[TestCategory("Gen2")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class ArchiveTests
|
public class ArchiveTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.Armageddon
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="GeneratedMap"/> class.
|
/// Represents a collection of tests for the <see cref="GeneratedMap"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("GeneratedMap")]
|
[TestCategory("Armageddon")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class GeneratedMapTests
|
public class GeneratedMapTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.Armageddon
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="LandData"/> class.
|
/// Represents a collection of tests for the <see cref="LandData"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("LandData (Armageddon)")]
|
[TestCategory("Armageddon")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class LandDataTests
|
public class LandDataTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.Armageddon.ProjectX
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="Library"/> class.
|
/// Represents a collection of tests for the <see cref="Library"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("Library")]
|
[TestCategory("ProjectX")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class LibraryTests
|
public class LibraryTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.Armageddon.ProjectX
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="Scheme"/> class.
|
/// Represents a collection of tests for the <see cref="Scheme"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("Scheme (ProjectX)")]
|
[TestCategory("ProjectX")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class SchemeTests
|
public class SchemeTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.Armageddon
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="Scheme"/> class.
|
/// Represents a collection of tests for the <see cref="Scheme"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("Scheme")]
|
[TestCategory("Armageddon")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class SchemeTests
|
public class SchemeTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.Armageddon
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="TeamContainer"/> class.
|
/// Represents a collection of tests for the <see cref="TeamContainer"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("TeamContainer (Armageddon)")]
|
[TestCategory("Armageddon")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class TeamContainerTests
|
public class TeamContainerTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="Image"/> class.
|
/// Represents a collection of tests for the <see cref="Image"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("Image")]
|
[TestCategory("Gen2")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class ImageTests
|
public class ImageTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="Palette"/> class.
|
/// Represents a collection of tests for the <see cref="Palette"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("Palette")]
|
[TestCategory("Gen2")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class PaletteTests
|
public class PaletteTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.WorldParty
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="LandData"/> class.
|
/// Represents a collection of tests for the <see cref="LandData"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("LandData (WorldParty)")]
|
[TestCategory("WorldParty")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class LandDataTests
|
public class LandDataTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.WorldParty
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="TeamContainer"/> class.
|
/// Represents a collection of tests for the <see cref="TeamContainer"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("TeamContainer (WorldParty)")]
|
[TestCategory("WorldParty")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class TeamContainerTests
|
public class TeamContainerTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.Worms2
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="LandData"/> class.
|
/// Represents a collection of tests for the <see cref="LandData"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("LandData (Worms2)")]
|
[TestCategory("Worms2")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class LandDataTests
|
public class LandDataTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.Worms2
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="SchemeOptions"/> class.
|
/// Represents a collection of tests for the <see cref="SchemeOptions"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("SchemeOptions")]
|
[TestCategory("Worms2")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class SchemeOptionsTests
|
public class SchemeOptionsTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.Worms2
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="SchemeWeapons"/> class.
|
/// Represents a collection of tests for the <see cref="SchemeWeapons"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("SchemeWeapons")]
|
[TestCategory("Worms2")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class SchemeWeaponsTests
|
public class SchemeWeaponsTests
|
||||||
{
|
{
|
||||||
|
@ -7,7 +7,7 @@ namespace Syroot.Worms.UnitTest.Gen2.Worms2
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents a collection of tests for the <see cref="TeamContainer"/> class.
|
/// Represents a collection of tests for the <see cref="TeamContainer"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[TestCategory("TeamContainer (Worms2)")]
|
[TestCategory("Worms2")]
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class TeamContainerTests
|
public class TeamContainerTests
|
||||||
{
|
{
|
||||||
|
@ -32,9 +32,9 @@ namespace Syroot.Worms.Core
|
|||||||
/// <param name="values">The instances to write into the current stream.</param>
|
/// <param name="values">The instances to write into the current stream.</param>
|
||||||
internal static void Save<T>(this BinaryDataWriter self, T[] values) where T : ISaveable
|
internal static void Save<T>(this BinaryDataWriter self, T[] values) where T : ISaveable
|
||||||
{
|
{
|
||||||
for (int i = 0; i < values.Length; i++)
|
foreach (T value in values)
|
||||||
{
|
{
|
||||||
Save(self, values[i]);
|
Save(self, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -43,7 +43,7 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
{
|
{
|
||||||
using (BinaryDataWriter writer = new BinaryDataWriter(stream, Encoding.ASCII, true))
|
using (BinaryDataWriter writer = new BinaryDataWriter(stream, Encoding.ASCII, true))
|
||||||
{
|
{
|
||||||
writer.Seek(4);
|
writer.Write(0);
|
||||||
writer.Write(Sprite);
|
writer.Write(Sprite);
|
||||||
writer.Write(HomeStyle);
|
writer.Write(HomeStyle);
|
||||||
writer.Write(Delay);
|
writer.Write(Delay);
|
||||||
|
@ -1,27 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.IO;
|
|
||||||
using Syroot.Worms.Core;
|
|
||||||
|
|
||||||
namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|
||||||
{
|
|
||||||
public class AttachedFile : ILoadable, ISaveable
|
|
||||||
{
|
|
||||||
// ---- PROPERTIES ---------------------------------------------------------------------------------------------
|
|
||||||
|
|
||||||
public string Name { get; set; }
|
|
||||||
|
|
||||||
public byte[] Data { get; set; }
|
|
||||||
|
|
||||||
// ---- METHODS (PUBLIC) ---------------------------------------------------------------------------------------
|
|
||||||
|
|
||||||
public void Load(Stream stream)
|
|
||||||
{
|
|
||||||
throw new NotImplementedException();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Save(Stream stream)
|
|
||||||
{
|
|
||||||
throw new NotImplementedException();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -135,7 +135,7 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
writer.Write(Count);
|
writer.Write(Count);
|
||||||
foreach (LibraryItem item in this)
|
foreach (LibraryItem item in this)
|
||||||
{
|
{
|
||||||
writer.Write(item.Type);
|
writer.Write(item.Type, true);
|
||||||
writer.Write(item.Key, BinaryStringFormat.DwordLengthPrefix);
|
writer.Write(item.Key, BinaryStringFormat.DwordLengthPrefix);
|
||||||
switch (item.Type)
|
switch (item.Type)
|
||||||
{
|
{
|
||||||
|
@ -116,16 +116,12 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
|
|
||||||
// Read required libraries.
|
// Read required libraries.
|
||||||
int librariesCount = reader.ReadInt32();
|
int librariesCount = reader.ReadInt32();
|
||||||
Libraries = new List<string>(librariesCount);
|
Libraries = new List<string>(reader.ReadStrings(librariesCount, BinaryStringFormat.DwordLengthPrefix));
|
||||||
for (int i = 0; i < librariesCount; i++)
|
|
||||||
{
|
|
||||||
Libraries.Add(reader.ReadString(BinaryStringFormat.DwordLengthPrefix));
|
|
||||||
}
|
|
||||||
|
|
||||||
// Read a possibly attached scheme file.
|
// Read a possibly attached scheme file.
|
||||||
if (reader.ReadBoolean())
|
if (reader.ReadBoolean())
|
||||||
{
|
{
|
||||||
int schemeLength = reader.ReadInt32(); // TODO: Check if required due to intelligent loading.
|
reader.Seek(sizeof(int)); // Scheme length not required due to intelligent loading.
|
||||||
GameScheme = reader.Load<Armageddon.Scheme>();
|
GameScheme = reader.Load<Armageddon.Scheme>();
|
||||||
GameSchemeName = reader.ReadString(BinaryStringFormat.DwordLengthPrefix);
|
GameSchemeName = reader.ReadString(BinaryStringFormat.DwordLengthPrefix);
|
||||||
}
|
}
|
||||||
@ -153,6 +149,55 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
using (BinaryDataWriter writer = new BinaryDataWriter(stream, Encoding.ASCII))
|
using (BinaryDataWriter writer = new BinaryDataWriter(stream, Encoding.ASCII))
|
||||||
{
|
{
|
||||||
// Write the header.
|
// Write the header.
|
||||||
|
writer.Write(_signature, BinaryStringFormat.NoPrefixOrTermination);
|
||||||
|
writer.Write(Version);
|
||||||
|
|
||||||
|
// Write the scheme flags.
|
||||||
|
writer.Write(Flags);
|
||||||
|
|
||||||
|
// Write the weapon tables.
|
||||||
|
writer.Write(WeaponTables.Count);
|
||||||
|
foreach (Weapon[] weaponTable in WeaponTables)
|
||||||
|
{
|
||||||
|
writer.Save(weaponTable);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Write a placeholder array.
|
||||||
|
writer.Write(0);
|
||||||
|
|
||||||
|
// Write attached files.
|
||||||
|
writer.Write(Files.Count);
|
||||||
|
foreach (KeyValuePair<string, byte[]> file in Files)
|
||||||
|
{
|
||||||
|
writer.Write(file.Key, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(file.Value.Length);
|
||||||
|
writer.Write(file.Value);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Write attached scripts.
|
||||||
|
writer.Write(Scripts.Count);
|
||||||
|
foreach (KeyValuePair<string, string> script in Scripts)
|
||||||
|
{
|
||||||
|
writer.Write(script.Key, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(script.Value, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Write required libraries.
|
||||||
|
writer.Write(Libraries.Count);
|
||||||
|
writer.Write(Libraries.ToArray());
|
||||||
|
|
||||||
|
// Write a possibly attached scheme file.
|
||||||
|
if (GameScheme != null)
|
||||||
|
{
|
||||||
|
byte[] schemeBytes;
|
||||||
|
using (MemoryStream schemeStream = new MemoryStream())
|
||||||
|
{
|
||||||
|
GameScheme.Save(schemeStream);
|
||||||
|
schemeBytes = schemeStream.ToArray();
|
||||||
|
}
|
||||||
|
writer.Write(schemeBytes.Length);
|
||||||
|
writer.Write(GameSchemeName, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -104,7 +104,7 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
|
|
||||||
reader.Position = offset + 180;
|
reader.Position = offset + 180;
|
||||||
ExplosionTarget = reader.ReadEnum<ExplosionTarget>(true);
|
ExplosionTarget = reader.ReadEnum<ExplosionTarget>(true);
|
||||||
reader.Seek(4);
|
reader.Seek(sizeof(int));
|
||||||
switch (ExplosionTarget)
|
switch (ExplosionTarget)
|
||||||
{
|
{
|
||||||
case ExplosionTarget.Clusters:
|
case ExplosionTarget.Clusters:
|
||||||
@ -125,7 +125,37 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
{
|
{
|
||||||
using (BinaryDataWriter writer = new BinaryDataWriter(stream, Encoding.ASCII, true))
|
using (BinaryDataWriter writer = new BinaryDataWriter(stream, Encoding.ASCII, true))
|
||||||
{
|
{
|
||||||
|
long offset = writer.Position;
|
||||||
|
|
||||||
|
writer.Write(SpriteSize);
|
||||||
|
writer.Write(FixedSpeed);
|
||||||
|
writer.Write(RunAway, BinaryBooleanFormat.NonZeroDword);
|
||||||
|
writer.Write(Collisions, true);
|
||||||
|
writer.Write(ExplosionBias);
|
||||||
|
writer.Write(ExplosionPushPower);
|
||||||
|
writer.Write(ExplosionDamage);
|
||||||
|
writer.Write(ExplosionDamageVariation);
|
||||||
|
writer.Write(ExplosionUnknown);
|
||||||
|
writer.Write(Sprite);
|
||||||
|
writer.Write(VariableSpeed);
|
||||||
|
writer.Write(WindFactor);
|
||||||
|
writer.Write(MotionRandomness);
|
||||||
|
writer.Write(GravityFactor);
|
||||||
|
writer.Write(ExplosionCountdown);
|
||||||
|
writer.Write(ExplosionTimer);
|
||||||
|
writer.Write(Sound);
|
||||||
|
writer.Write(ExplodeOnSpace, BinaryBooleanFormat.NonZeroDword);
|
||||||
|
|
||||||
|
writer.Write(ExplosionAction, true);
|
||||||
|
writer.Save(Action);
|
||||||
|
|
||||||
|
writer.Position = offset + 180;
|
||||||
|
writer.Write(ExplosionTarget, true);
|
||||||
|
writer.Seek(sizeof(int));
|
||||||
|
if (ExplosionTarget != ExplosionTarget.None)
|
||||||
|
{
|
||||||
|
writer.Save(Target);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -121,6 +121,7 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
writer.Write(ExplosionPushPower);
|
writer.Write(ExplosionPushPower);
|
||||||
writer.Write(ExplosionDamage);
|
writer.Write(ExplosionDamage);
|
||||||
writer.Write(ExplosionDamageVariation);
|
writer.Write(ExplosionDamageVariation);
|
||||||
|
writer.Write(SpriteCount);
|
||||||
writer.Write(Sprite);
|
writer.Write(Sprite);
|
||||||
writer.Write(Acceleration);
|
writer.Write(Acceleration);
|
||||||
writer.Write(WindResponse);
|
writer.Write(WindResponse);
|
||||||
@ -131,7 +132,7 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
writer.Write(Sound);
|
writer.Write(Sound);
|
||||||
writer.Write(ExplodeOnSpace, BinaryBooleanFormat.NonZeroDword);
|
writer.Write(ExplodeOnSpace, BinaryBooleanFormat.NonZeroDword);
|
||||||
|
|
||||||
writer.Write(ExplosionAction);
|
writer.Write(ExplosionAction, true);
|
||||||
writer.Save(Action);
|
writer.Save(Action);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -9,14 +9,9 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
[DebuggerDisplay("Weapon Name={Name}")]
|
[DebuggerDisplay("Weapon Name={Name}")]
|
||||||
public class Weapon : ILoadable, ISaveable
|
public class Weapon : ILoadable, ISaveable
|
||||||
{
|
{
|
||||||
// ---- CONSTANTS ----------------------------------------------------------------------------------------------
|
|
||||||
|
|
||||||
private const int _version_0_8_0_pre = 0x5ABBDD05;
|
|
||||||
private const int _version_0_8_0 = 0x5ABBDD06;
|
|
||||||
|
|
||||||
// ---- PROPERTIES ---------------------------------------------------------------------------------------------
|
// ---- PROPERTIES ---------------------------------------------------------------------------------------------
|
||||||
|
|
||||||
public int Version { get; set; }
|
public WeaponVersion Version { get; set; }
|
||||||
|
|
||||||
public long Checksum { get; set; }
|
public long Checksum { get; set; }
|
||||||
|
|
||||||
@ -38,7 +33,7 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
|
|
||||||
public int CrateCount { get; set; }
|
public int CrateCount { get; set; }
|
||||||
|
|
||||||
public bool Unknown2 { get; set; }
|
public int Unknown2 { get; set; }
|
||||||
|
|
||||||
public WeaponActivation Activation { get; set; }
|
public WeaponActivation Activation { get; set; }
|
||||||
|
|
||||||
@ -120,11 +115,7 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
{
|
{
|
||||||
// Read the header.
|
// Read the header.
|
||||||
long offset = reader.Position;
|
long offset = reader.Position;
|
||||||
Version = reader.ReadInt32();
|
Version = reader.ReadEnum<WeaponVersion>(true);
|
||||||
if (Version != _version_0_8_0_pre && Version != _version_0_8_0)
|
|
||||||
{
|
|
||||||
throw new InvalidDataException($"Unknown Project X weapon version 0x{Version:X8}.");
|
|
||||||
}
|
|
||||||
Checksum = reader.ReadInt64();
|
Checksum = reader.ReadInt64();
|
||||||
|
|
||||||
// Read general settings.
|
// Read general settings.
|
||||||
@ -137,7 +128,7 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
Unknown1 = reader.ReadInt32();
|
Unknown1 = reader.ReadInt32();
|
||||||
CrateChance = reader.ReadInt32();
|
CrateChance = reader.ReadInt32();
|
||||||
CrateCount = reader.ReadInt32();
|
CrateCount = reader.ReadInt32();
|
||||||
Unknown2 = reader.ReadBoolean(BinaryBooleanFormat.NonZeroDword);
|
Unknown2 = reader.ReadInt32();
|
||||||
|
|
||||||
// Read the activation and the corresponding weapon settings.
|
// Read the activation and the corresponding weapon settings.
|
||||||
Activation = reader.ReadEnum<WeaponActivation>(true);
|
Activation = reader.ReadEnum<WeaponActivation>(true);
|
||||||
@ -277,7 +268,7 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
AimSpriteOverride = reader.ReadBoolean();
|
AimSpriteOverride = reader.ReadBoolean();
|
||||||
PickSpriteOverride = reader.ReadBoolean();
|
PickSpriteOverride = reader.ReadBoolean();
|
||||||
FireSpriteOverride = reader.ReadBoolean();
|
FireSpriteOverride = reader.ReadBoolean();
|
||||||
if (Version == _version_0_8_0)
|
if (Version == WeaponVersion.Version_0_8_0)
|
||||||
{
|
{
|
||||||
Utility = reader.ReadBoolean();
|
Utility = reader.ReadBoolean();
|
||||||
}
|
}
|
||||||
@ -292,11 +283,118 @@ namespace Syroot.Worms.Gen2.Armageddon.ProjectX
|
|||||||
{
|
{
|
||||||
using (BinaryDataWriter writer = new BinaryDataWriter(stream, Encoding.ASCII, true))
|
using (BinaryDataWriter writer = new BinaryDataWriter(stream, Encoding.ASCII, true))
|
||||||
{
|
{
|
||||||
|
// Write the header.
|
||||||
|
long offset = writer.Position;
|
||||||
|
writer.Write(Version, true);
|
||||||
|
writer.Write(Checksum);
|
||||||
|
|
||||||
|
// Write the general settings.
|
||||||
|
writer.Write(TableRow);
|
||||||
|
writer.Write(Remembered, BinaryBooleanFormat.NonZeroDword);
|
||||||
|
writer.Write(UsableInCavern, BinaryBooleanFormat.NonZeroDword);
|
||||||
|
writer.Write(Shots);
|
||||||
|
writer.Write(ShotEndsTurn, BinaryBooleanFormat.NonZeroDword);
|
||||||
|
writer.Write(RetreatTime);
|
||||||
|
writer.Write(Unknown1);
|
||||||
|
writer.Write(CrateChance);
|
||||||
|
writer.Write(CrateCount);
|
||||||
|
writer.Write(Unknown2);
|
||||||
|
|
||||||
|
// Write the activation and the corresponding weapon settings.
|
||||||
|
writer.Write(Activation, true);
|
||||||
|
switch (Activation)
|
||||||
|
{
|
||||||
|
case WeaponActivation.Airstrike:
|
||||||
|
writer.Write(AirstrikeSubtype);
|
||||||
|
writer.Save(Style);
|
||||||
|
break;
|
||||||
|
case WeaponActivation.Crosshair:
|
||||||
|
writer.Seek(sizeof(int));
|
||||||
|
writer.Write(CrosshairAction, true);
|
||||||
|
if (CrosshairAction != WeaponCrosshairAction.None)
|
||||||
|
{
|
||||||
|
writer.Save(Style);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case WeaponActivation.Spacebar:
|
||||||
|
writer.Write(SpacebarAction, true);
|
||||||
|
switch (SpacebarAction)
|
||||||
|
{
|
||||||
|
case WeaponSpacebarAction.Armageddon:
|
||||||
|
case WeaponSpacebarAction.BaseballBat:
|
||||||
|
case WeaponSpacebarAction.BattleAxe:
|
||||||
|
case WeaponSpacebarAction.Blowtorch:
|
||||||
|
case WeaponSpacebarAction.Dragonball:
|
||||||
|
case WeaponSpacebarAction.Firepunch:
|
||||||
|
case WeaponSpacebarAction.Jetpack:
|
||||||
|
case WeaponSpacebarAction.Kamikaze:
|
||||||
|
case WeaponSpacebarAction.NinjaRope:
|
||||||
|
case WeaponSpacebarAction.NuclearTest:
|
||||||
|
case WeaponSpacebarAction.Parachute:
|
||||||
|
case WeaponSpacebarAction.PneumaticDrill:
|
||||||
|
case WeaponSpacebarAction.Prod:
|
||||||
|
case WeaponSpacebarAction.SuicideBomber:
|
||||||
|
writer.Save(Style);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case WeaponActivation.Throw:
|
||||||
|
writer.Write(ThrowHerdCount);
|
||||||
|
writer.Write(ThrowAction, true);
|
||||||
|
if (ThrowAction != WeaponThrowAction.None)
|
||||||
|
{
|
||||||
|
writer.Save(Style);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Write additional settings.
|
||||||
|
writer.Position = offset + 468;
|
||||||
|
writer.Write(AmmunitionOverride, BinaryBooleanFormat.NonZeroDword);
|
||||||
|
writer.Write(Ammunition);
|
||||||
|
writer.Write(Unknown3);
|
||||||
|
writer.Write(WeaponSprite);
|
||||||
|
writer.Write(NameLong, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(Name, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(GridImageFile, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(GfxDirectoryFile, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(SpriteNames, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(DelayOverride, BinaryBooleanFormat.NonZeroDword);
|
||||||
|
writer.Write(Delay);
|
||||||
|
|
||||||
|
writer.Write(UseLibrary);
|
||||||
|
if (UseLibrary)
|
||||||
|
{
|
||||||
|
writer.Write(LibraryName, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(LibraryWeaponName, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
}
|
||||||
|
|
||||||
|
writer.Write(AimSpriteEven, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(AimSpriteUphill, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(AimSpriteDownhill, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(PickSpriteEven, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(PickSpriteUphill, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(PickSpriteDownhill, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(FireSpriteEven, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(FireSpriteUphill, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(FireSpriteDownhill, BinaryStringFormat.DwordLengthPrefix);
|
||||||
|
writer.Write(AimSpriteOverride);
|
||||||
|
writer.Write(PickSpriteOverride);
|
||||||
|
writer.Write(FireSpriteOverride);
|
||||||
|
if (Version == WeaponVersion.Version_0_8_0)
|
||||||
|
{
|
||||||
|
writer.Write(Utility);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public enum WeaponVersion : int
|
||||||
|
{
|
||||||
|
Version_0_8_0_pre = 0x5ABBDD05,
|
||||||
|
Version_0_8_0 = 0x5ABBDD06
|
||||||
|
}
|
||||||
|
|
||||||
public enum WeaponActivation : int
|
public enum WeaponActivation : int
|
||||||
{
|
{
|
||||||
None,
|
None,
|
||||||
|
Loading…
x
Reference in New Issue
Block a user