mirror of
https://github.com/crskycode/GARbro.git
synced 2024-11-23 21:55:34 +08:00
added callback into archive creation method.
This commit is contained in:
parent
c13b9bb12e
commit
08b8e8a46b
@ -284,11 +284,9 @@ namespace GameRes.Formats
|
|||||||
return widget.GetKey();
|
return widget.GetKey();
|
||||||
}
|
}
|
||||||
|
|
||||||
public override ResourceOptions GetOptions ()
|
public override object GetAccessWidget ()
|
||||||
{
|
{
|
||||||
return new ResourceOptions {
|
return new GUI.WidgetINT (Settings.Default.INTEncryption ?? new IntEncryptionInfo());
|
||||||
Widget = new GUI.WidgetINT (Settings.Default.INTEncryption ?? new IntEncryptionInfo())
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -273,11 +273,9 @@ namespace GameRes.Formats
|
|||||||
return table;
|
return table;
|
||||||
}
|
}
|
||||||
|
|
||||||
public override ResourceOptions GetOptions ()
|
public override object GetAccessWidget ()
|
||||||
{
|
{
|
||||||
return new ResourceOptions {
|
return new GUI.WidgetNPA();
|
||||||
Widget = new GUI.WidgetNPA()
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
|
|
||||||
NpaTitleId QueryGameEncryption ()
|
NpaTitleId QueryGameEncryption ()
|
||||||
|
@ -54,7 +54,8 @@ namespace GameRes.Formats
|
|||||||
return new ArcFile (file, this, dir);
|
return new ArcFile (file, this, dir);
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void Create (Stream output, IEnumerable<Entry> list, ResourceOptions options)
|
public override void Create (Stream output, IEnumerable<Entry> list, ResourceOptions options,
|
||||||
|
EntryCallback callback)
|
||||||
{
|
{
|
||||||
using (var writer = new BinaryWriter (output, Encoding.ASCII, true))
|
using (var writer = new BinaryWriter (output, Encoding.ASCII, true))
|
||||||
{
|
{
|
||||||
@ -68,6 +69,10 @@ namespace GameRes.Formats
|
|||||||
encoding.EncoderFallback = EncoderFallback.ExceptionFallback;
|
encoding.EncoderFallback = EncoderFallback.ExceptionFallback;
|
||||||
|
|
||||||
byte[] name_buf = new byte[32];
|
byte[] name_buf = new byte[32];
|
||||||
|
int callback_count = 0;
|
||||||
|
|
||||||
|
if (null != callback)
|
||||||
|
callback (callback_count++, null, "Writing index...");
|
||||||
|
|
||||||
// first, write names only
|
// first, write names only
|
||||||
foreach (var entry in list)
|
foreach (var entry in list)
|
||||||
@ -95,6 +100,9 @@ namespace GameRes.Formats
|
|||||||
uint current_offset = 0;
|
uint current_offset = 0;
|
||||||
foreach (var entry in list)
|
foreach (var entry in list)
|
||||||
{
|
{
|
||||||
|
if (null != callback)
|
||||||
|
callback (callback_count++, entry, "Adding file");
|
||||||
|
|
||||||
entry.Offset = current_offset;
|
entry.Offset = current_offset;
|
||||||
using (var input = File.Open (entry.Name, FileMode.Open, FileAccess.Read))
|
using (var input = File.Open (entry.Name, FileMode.Open, FileAccess.Read))
|
||||||
{
|
{
|
||||||
@ -107,6 +115,9 @@ namespace GameRes.Formats
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (null != callback)
|
||||||
|
callback (callback_count++, null, "Updating index...");
|
||||||
|
|
||||||
// at last, go back to directory and write offset/sizes
|
// at last, go back to directory and write offset/sizes
|
||||||
long dir_offset = 12+32;
|
long dir_offset = 12+32;
|
||||||
foreach (var entry in list)
|
foreach (var entry in list)
|
||||||
|
@ -39,6 +39,15 @@ namespace GameRes.Formats.KiriKiri
|
|||||||
public uint Hash { get; set; }
|
public uint Hash { get; set; }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public class Xp3Options : ResourceOptions
|
||||||
|
{
|
||||||
|
public int Version { get; set; }
|
||||||
|
public ICrypt Scheme { get; set; }
|
||||||
|
public bool CompressIndex { get; set; }
|
||||||
|
public bool CompressContents { get; set; }
|
||||||
|
public bool RetainDirs { get; set; }
|
||||||
|
}
|
||||||
|
|
||||||
// Archive version 1: encrypt file first, then calculate checksum
|
// Archive version 1: encrypt file first, then calculate checksum
|
||||||
// version 2: calculate checksum, then encrypt
|
// version 2: calculate checksum, then encrypt
|
||||||
|
|
||||||
@ -229,16 +238,41 @@ NextEntry:
|
|||||||
return new Xp3Stream (arc.File, xp3_entry);
|
return new Xp3Stream (arc.File, xp3_entry);
|
||||||
}
|
}
|
||||||
|
|
||||||
public override ResourceOptions GetOptions ()
|
public override ResourceOptions GetDefaultOptions ()
|
||||||
{
|
{
|
||||||
return new ResourceOptions {
|
return new Xp3Options {
|
||||||
Widget = new GUI.CreateXP3Widget()
|
Version = Settings.Default.XP3Version,
|
||||||
|
Scheme = NoCryptAlgorithm,
|
||||||
|
CompressIndex = Settings.Default.XP3CompressHeader,
|
||||||
|
CompressContents = Settings.Default.XP3CompressContents,
|
||||||
|
RetainDirs = Settings.Default.XP3RetainStructure,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public override ResourceOptions GetOptions (object widget)
|
||||||
|
{
|
||||||
|
var options = this.GetDefaultOptions() as Xp3Options;
|
||||||
|
var w = widget as GUI.CreateXP3Widget;
|
||||||
|
if (null != w)
|
||||||
|
{
|
||||||
|
options.Scheme = w.EncryptionWidget.GetScheme();
|
||||||
|
}
|
||||||
|
return options;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override object GetCreationWidget ()
|
||||||
|
{
|
||||||
|
return new GUI.CreateXP3Widget();
|
||||||
|
}
|
||||||
|
|
||||||
|
public override object GetAccessWidget ()
|
||||||
|
{
|
||||||
|
return new GUI.WidgetXP3();
|
||||||
|
}
|
||||||
|
|
||||||
ICrypt QueryCryptAlgorithm ()
|
ICrypt QueryCryptAlgorithm ()
|
||||||
{
|
{
|
||||||
var widget = new GUI.WidgetXP3();
|
var widget = this.GetAccessWidget() as GUI.WidgetXP3;
|
||||||
var args = new ParametersRequestEventArgs
|
var args = new ParametersRequestEventArgs
|
||||||
{
|
{
|
||||||
Notice = arcStrings.ArcEncryptedNotice,
|
Notice = arcStrings.ArcEncryptedNotice,
|
||||||
@ -280,25 +314,24 @@ NextEntry:
|
|||||||
(byte)'X', (byte)'P', (byte)'3', 0x0d, 0x0a, 0x20, 0x0a, 0x1a, 0x8b, 0x67, 0x01
|
(byte)'X', (byte)'P', (byte)'3', 0x0d, 0x0a, 0x20, 0x0a, 0x1a, 0x8b, 0x67, 0x01
|
||||||
};
|
};
|
||||||
|
|
||||||
public override void Create (Stream output, IEnumerable<Entry> list, ResourceOptions options)
|
public override void Create (Stream output, IEnumerable<Entry> list, ResourceOptions options,
|
||||||
|
EntryCallback callback)
|
||||||
{
|
{
|
||||||
int version = Settings.Default.XP3Version;
|
var xp3_options = options as Xp3Options;
|
||||||
ICrypt scheme = NoCryptAlgorithm;
|
if (null == xp3_options)
|
||||||
bool compress_header = Settings.Default.XP3CompressHeader;
|
xp3_options = this.GetDefaultOptions() as Xp3Options;
|
||||||
bool compress_contents = Settings.Default.XP3CompressContents;
|
|
||||||
bool retain_dirs = Settings.Default.XP3RetainStructure;
|
ICrypt scheme = xp3_options.Scheme;
|
||||||
|
bool compress_index = xp3_options.CompressIndex;
|
||||||
|
bool compress_contents = xp3_options.CompressContents;
|
||||||
|
bool retain_dirs = xp3_options.RetainDirs;
|
||||||
|
|
||||||
var widget = options.Widget as GUI.CreateXP3Widget;
|
|
||||||
if (null != widget)
|
|
||||||
{
|
|
||||||
scheme = widget.EncryptionWidget.GetScheme();
|
|
||||||
}
|
|
||||||
bool use_encryption = scheme != NoCryptAlgorithm;
|
bool use_encryption = scheme != NoCryptAlgorithm;
|
||||||
|
|
||||||
using (var writer = new BinaryWriter (output, Encoding.ASCII, true))
|
using (var writer = new BinaryWriter (output, Encoding.ASCII, true))
|
||||||
{
|
{
|
||||||
writer.Write (s_xp3_header);
|
writer.Write (s_xp3_header);
|
||||||
if (2 == version)
|
if (2 == xp3_options.Version)
|
||||||
{
|
{
|
||||||
writer.Write ((long)0x17);
|
writer.Write ((long)0x17);
|
||||||
writer.Write ((int)1);
|
writer.Write ((int)1);
|
||||||
@ -308,11 +341,15 @@ NextEntry:
|
|||||||
long index_pos_offset = writer.BaseStream.Position;
|
long index_pos_offset = writer.BaseStream.Position;
|
||||||
writer.BaseStream.Seek (8, SeekOrigin.Current);
|
writer.BaseStream.Seek (8, SeekOrigin.Current);
|
||||||
|
|
||||||
|
int callback_count = 0;
|
||||||
var used_names = new HashSet<string>();
|
var used_names = new HashSet<string>();
|
||||||
var dir = new List<Xp3Entry>();
|
var dir = new List<Xp3Entry>();
|
||||||
long current_offset = writer.BaseStream.Position;
|
long current_offset = writer.BaseStream.Position;
|
||||||
foreach (var entry in list)
|
foreach (var entry in list)
|
||||||
{
|
{
|
||||||
|
if (null != callback)
|
||||||
|
callback (callback_count++, entry, arcStrings.MsgAddingFile);
|
||||||
|
|
||||||
string name = entry.Name;
|
string name = entry.Name;
|
||||||
if (!retain_dirs)
|
if (!retain_dirs)
|
||||||
name = Path.GetFileName (name);
|
name = Path.GetFileName (name);
|
||||||
@ -330,10 +367,13 @@ NextEntry:
|
|||||||
Cipher = scheme,
|
Cipher = scheme,
|
||||||
};
|
};
|
||||||
bool compress = compress_contents && ShouldCompressFile (entry);
|
bool compress = compress_contents && ShouldCompressFile (entry);
|
||||||
if (!use_encryption)
|
using (var file = File.Open (name, FileMode.Open, FileAccess.Read))
|
||||||
RawFileCopy (entry.Name, xp3entry, output, compress);
|
{
|
||||||
else
|
if (!use_encryption || 0 == file.Length)
|
||||||
EncryptedFileCopy (entry.Name, xp3entry, output, compress);
|
RawFileCopy (file, xp3entry, output, compress);
|
||||||
|
else
|
||||||
|
EncryptedFileCopy (file, xp3entry, output, compress);
|
||||||
|
}
|
||||||
|
|
||||||
dir.Add (xp3entry);
|
dir.Add (xp3entry);
|
||||||
}
|
}
|
||||||
@ -345,6 +385,9 @@ NextEntry:
|
|||||||
|
|
||||||
using (var header = new BinaryWriter (new MemoryStream (dir.Count*0x58), Encoding.Unicode))
|
using (var header = new BinaryWriter (new MemoryStream (dir.Count*0x58), Encoding.Unicode))
|
||||||
{
|
{
|
||||||
|
if (null != callback)
|
||||||
|
callback (callback_count++, null, arcStrings.MsgWritingIndex);
|
||||||
|
|
||||||
long dir_pos = 0;
|
long dir_pos = 0;
|
||||||
foreach (var entry in dir)
|
foreach (var entry in dir)
|
||||||
{
|
{
|
||||||
@ -381,10 +424,13 @@ NextEntry:
|
|||||||
}
|
}
|
||||||
|
|
||||||
header.BaseStream.Position = 0;
|
header.BaseStream.Position = 0;
|
||||||
writer.Write ((byte)(compress_header ? 1 : 0));
|
writer.Write ((byte)(compress_index ? 1 : 0));
|
||||||
long unpacked_dir_size = header.BaseStream.Length;
|
long unpacked_dir_size = header.BaseStream.Length;
|
||||||
if (compress_header)
|
if (compress_index)
|
||||||
{
|
{
|
||||||
|
if (null != callback)
|
||||||
|
callback (callback_count++, null, arcStrings.MsgCompressingIndex);
|
||||||
|
|
||||||
long packed_dir_size_pos = writer.BaseStream.Position;
|
long packed_dir_size_pos = writer.BaseStream.Position;
|
||||||
writer.Write ((long)0);
|
writer.Write ((long)0);
|
||||||
writer.Write (unpacked_dir_size);
|
writer.Write (unpacked_dir_size);
|
||||||
@ -407,48 +453,45 @@ NextEntry:
|
|||||||
output.Seek (0, SeekOrigin.End);
|
output.Seek (0, SeekOrigin.End);
|
||||||
}
|
}
|
||||||
|
|
||||||
void RawFileCopy (string name, Xp3Entry xp3entry, Stream output, bool compress)
|
void RawFileCopy (FileStream file, Xp3Entry xp3entry, Stream output, bool compress)
|
||||||
{
|
{
|
||||||
using (var file = File.Open (name, FileMode.Open, FileAccess.Read))
|
if (file.Length > uint.MaxValue)
|
||||||
{
|
throw new FileSizeException();
|
||||||
if (file.Length > uint.MaxValue)
|
|
||||||
throw new FileSizeException();
|
|
||||||
|
|
||||||
uint unpacked_size = (uint)file.Length;
|
uint unpacked_size = (uint)file.Length;
|
||||||
xp3entry.UnpackedSize = (uint)unpacked_size;
|
xp3entry.UnpackedSize = (uint)unpacked_size;
|
||||||
xp3entry.Size = (uint)unpacked_size;
|
xp3entry.Size = (uint)unpacked_size;
|
||||||
var segment = new Xp3Segment {
|
compress = compress && unpacked_size > 0;
|
||||||
IsCompressed = compress,
|
var segment = new Xp3Segment {
|
||||||
Offset = output.Position,
|
IsCompressed = compress,
|
||||||
Size = unpacked_size,
|
Offset = output.Position,
|
||||||
PackedSize = unpacked_size
|
Size = unpacked_size,
|
||||||
};
|
PackedSize = unpacked_size
|
||||||
if (compress)
|
};
|
||||||
|
if (compress)
|
||||||
|
{
|
||||||
|
using (var zstream = new ZLibStream (output, CompressionMode.Compress, true))
|
||||||
{
|
{
|
||||||
using (var zstream = new ZLibStream (output, CompressionMode.Compress, true))
|
xp3entry.Hash = CheckedCopy (file, zstream);
|
||||||
{
|
zstream.Flush();
|
||||||
xp3entry.Hash = CheckedCopy (file, zstream);
|
segment.PackedSize = (uint)zstream.TotalOut;
|
||||||
zstream.Flush();
|
|
||||||
segment.PackedSize = (uint)zstream.TotalOut;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else
|
|
||||||
{
|
|
||||||
xp3entry.Hash = CheckedCopy (file, output);
|
|
||||||
}
|
|
||||||
xp3entry.Segments.Add (segment);
|
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
xp3entry.Hash = CheckedCopy (file, output);
|
||||||
|
}
|
||||||
|
xp3entry.Segments.Add (segment);
|
||||||
}
|
}
|
||||||
|
|
||||||
void EncryptedFileCopy (string name, Xp3Entry xp3entry, Stream output, bool compress)
|
void EncryptedFileCopy (FileStream file, Xp3Entry xp3entry, Stream output, bool compress)
|
||||||
{
|
{
|
||||||
var file = File.Open (name, FileMode.Open, FileAccess.Read);
|
if (file.Length > int.MaxValue)
|
||||||
using (var map = MemoryMappedFile.CreateFromFile (file, null, 0,
|
throw new FileSizeException();
|
||||||
MemoryMappedFileAccess.Read, null, HandleInheritability.None, false))
|
|
||||||
{
|
|
||||||
if (file.Length > int.MaxValue)
|
|
||||||
throw new FileSizeException();
|
|
||||||
|
|
||||||
|
using (var map = MemoryMappedFile.CreateFromFile (file, null, 0,
|
||||||
|
MemoryMappedFileAccess.Read, null, HandleInheritability.None, true))
|
||||||
|
{
|
||||||
uint unpacked_size = (uint)file.Length;
|
uint unpacked_size = (uint)file.Length;
|
||||||
xp3entry.UnpackedSize = (uint)unpacked_size;
|
xp3entry.UnpackedSize = (uint)unpacked_size;
|
||||||
xp3entry.Size = (uint)unpacked_size;
|
xp3entry.Size = (uint)unpacked_size;
|
||||||
@ -671,7 +714,7 @@ NextEntry:
|
|||||||
|
|
||||||
public virtual void Encrypt (Xp3Entry entry, long offset, byte[] values, int pos, int count)
|
public virtual void Encrypt (Xp3Entry entry, long offset, byte[] values, int pos, int count)
|
||||||
{
|
{
|
||||||
throw new NotImplementedException ("Encryption method not implemented");
|
throw new NotImplementedException (arcStrings.MsgEncNotImplemented);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
36
ArcFormats/Strings/arcStrings.Designer.cs
generated
36
ArcFormats/Strings/arcStrings.Designer.cs
generated
@ -171,6 +171,33 @@ namespace GameRes.Formats.Strings {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Looks up a localized string similar to Adding file.
|
||||||
|
/// </summary>
|
||||||
|
public static string MsgAddingFile {
|
||||||
|
get {
|
||||||
|
return ResourceManager.GetString("MsgAddingFile", resourceCulture);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Looks up a localized string similar to Compressing index....
|
||||||
|
/// </summary>
|
||||||
|
public static string MsgCompressingIndex {
|
||||||
|
get {
|
||||||
|
return ResourceManager.GetString("MsgCompressingIndex", resourceCulture);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Looks up a localized string similar to Encryption method not implemented.
|
||||||
|
/// </summary>
|
||||||
|
public static string MsgEncNotImplemented {
|
||||||
|
get {
|
||||||
|
return ResourceManager.GetString("MsgEncNotImplemented", resourceCulture);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Looks up a localized string similar to File name is too long.
|
/// Looks up a localized string similar to File name is too long.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -189,6 +216,15 @@ namespace GameRes.Formats.Strings {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Looks up a localized string similar to Writing index....
|
||||||
|
/// </summary>
|
||||||
|
public static string MsgWritingIndex {
|
||||||
|
get {
|
||||||
|
return ResourceManager.GetString("MsgWritingIndex", resourceCulture);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Looks up a localized string similar to Nitro+ resource archive.
|
/// Looks up a localized string similar to Nitro+ resource archive.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
@ -156,12 +156,24 @@ predefined encryption scheme.</value>
|
|||||||
<data name="LWGDescription" xml:space="preserve">
|
<data name="LWGDescription" xml:space="preserve">
|
||||||
<value>Liar-soft image archive</value>
|
<value>Liar-soft image archive</value>
|
||||||
</data>
|
</data>
|
||||||
|
<data name="MsgAddingFile" xml:space="preserve">
|
||||||
|
<value>Adding file</value>
|
||||||
|
</data>
|
||||||
|
<data name="MsgCompressingIndex" xml:space="preserve">
|
||||||
|
<value>Compressing index...</value>
|
||||||
|
</data>
|
||||||
|
<data name="MsgEncNotImplemented" xml:space="preserve">
|
||||||
|
<value>Encryption method not implemented</value>
|
||||||
|
</data>
|
||||||
<data name="MsgFileNameTooLong" xml:space="preserve">
|
<data name="MsgFileNameTooLong" xml:space="preserve">
|
||||||
<value>File name is too long</value>
|
<value>File name is too long</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="MsgIllegalCharacters" xml:space="preserve">
|
<data name="MsgIllegalCharacters" xml:space="preserve">
|
||||||
<value>File name contains illegal characters</value>
|
<value>File name contains illegal characters</value>
|
||||||
</data>
|
</data>
|
||||||
|
<data name="MsgWritingIndex" xml:space="preserve">
|
||||||
|
<value>Writing index...</value>
|
||||||
|
</data>
|
||||||
<data name="NPADescription" xml:space="preserve">
|
<data name="NPADescription" xml:space="preserve">
|
||||||
<value>Nitro+ resource archive</value>
|
<value>Nitro+ resource archive</value>
|
||||||
</data>
|
</data>
|
||||||
|
@ -141,12 +141,24 @@
|
|||||||
Введите ключ шифрования или выберите
|
Введите ключ шифрования или выберите
|
||||||
один из предопределённых вариантов.</value>
|
один из предопределённых вариантов.</value>
|
||||||
</data>
|
</data>
|
||||||
|
<data name="MsgAddingFile" xml:space="preserve">
|
||||||
|
<value>Добавляется файл</value>
|
||||||
|
</data>
|
||||||
|
<data name="MsgCompressingIndex" xml:space="preserve">
|
||||||
|
<value>Сжимается оглавление...</value>
|
||||||
|
</data>
|
||||||
|
<data name="MsgEncNotImplemented" xml:space="preserve">
|
||||||
|
<value>Метод шифрования не реализован</value>
|
||||||
|
</data>
|
||||||
<data name="MsgFileNameTooLong" xml:space="preserve">
|
<data name="MsgFileNameTooLong" xml:space="preserve">
|
||||||
<value>Слишком длинное имя файла</value>
|
<value>Слишком длинное имя файла</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="MsgIllegalCharacters" xml:space="preserve">
|
<data name="MsgIllegalCharacters" xml:space="preserve">
|
||||||
<value>Имя файла содержит недопустимые символы</value>
|
<value>Имя файла содержит недопустимые символы</value>
|
||||||
</data>
|
</data>
|
||||||
|
<data name="MsgWritingIndex" xml:space="preserve">
|
||||||
|
<value>Записывается оглавление...</value>
|
||||||
|
</data>
|
||||||
<data name="XP3CompressContents" xml:space="preserve">
|
<data name="XP3CompressContents" xml:space="preserve">
|
||||||
<value>Сжать содержимое</value>
|
<value>Сжать содержимое</value>
|
||||||
</data>
|
</data>
|
||||||
|
@ -11,13 +11,6 @@ using System.Diagnostics;
|
|||||||
|
|
||||||
namespace GameRes
|
namespace GameRes
|
||||||
{
|
{
|
||||||
public enum ExtractAction
|
|
||||||
{
|
|
||||||
Abort,
|
|
||||||
Skip,
|
|
||||||
Continue,
|
|
||||||
}
|
|
||||||
|
|
||||||
public class ArcFile : IDisposable
|
public class ArcFile : IDisposable
|
||||||
{
|
{
|
||||||
private ArcView m_arc;
|
private ArcView m_arc;
|
||||||
@ -36,8 +29,6 @@ namespace GameRes
|
|||||||
/// <summary>Archive contents.</summary>
|
/// <summary>Archive contents.</summary>
|
||||||
public ICollection<Entry> Dir { get { return m_dir; } }
|
public ICollection<Entry> Dir { get { return m_dir; } }
|
||||||
|
|
||||||
public delegate ExtractAction ExtractCallback (int num, Entry entry);
|
|
||||||
|
|
||||||
public ArcFile (ArcView arc, ArchiveFormat impl, ICollection<Entry> dir)
|
public ArcFile (ArcView arc, ArchiveFormat impl, ICollection<Entry> dir)
|
||||||
{
|
{
|
||||||
m_arc = arc;
|
m_arc = arc;
|
||||||
@ -93,15 +84,15 @@ namespace GameRes
|
|||||||
/// Extract all entries from the archive into current directory.
|
/// Extract all entries from the archive into current directory.
|
||||||
/// <paramref name="callback"/> could be used to observe/control extraction process.
|
/// <paramref name="callback"/> could be used to observe/control extraction process.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public void ExtractFiles (ExtractCallback callback)
|
public void ExtractFiles (EntryCallback callback)
|
||||||
{
|
{
|
||||||
int i = 0;
|
int i = 0;
|
||||||
foreach (var entry in Dir.OrderBy (e => e.Offset))
|
foreach (var entry in Dir.OrderBy (e => e.Offset))
|
||||||
{
|
{
|
||||||
var action = callback (i, entry);
|
var action = callback (i, entry, null);
|
||||||
if (ExtractAction.Abort == action)
|
if (ArchiveOperation.Abort == action)
|
||||||
break;
|
break;
|
||||||
if (ExtractAction.Skip != action)
|
if (ArchiveOperation.Skip != action)
|
||||||
Extract (entry);
|
Extract (entry);
|
||||||
++i;
|
++i;
|
||||||
}
|
}
|
||||||
|
@ -96,9 +96,17 @@ namespace GameRes
|
|||||||
|
|
||||||
public class ResourceOptions
|
public class ResourceOptions
|
||||||
{
|
{
|
||||||
public object Widget { get; set; }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public enum ArchiveOperation
|
||||||
|
{
|
||||||
|
Abort,
|
||||||
|
Skip,
|
||||||
|
Continue,
|
||||||
|
}
|
||||||
|
|
||||||
|
public delegate ArchiveOperation EntryCallback (int num, Entry entry, string description);
|
||||||
|
|
||||||
public abstract class ArchiveFormat : IResource
|
public abstract class ArchiveFormat : IResource
|
||||||
{
|
{
|
||||||
public override string Type { get { return "archive"; } }
|
public override string Type { get { return "archive"; } }
|
||||||
@ -149,12 +157,28 @@ namespace GameRes
|
|||||||
/// Create resource wihin stream <paramref name="file"/> containing entries from the
|
/// Create resource wihin stream <paramref name="file"/> containing entries from the
|
||||||
/// supplied <paramref name="list"/> and applying necessary <paramref name="options"/>.
|
/// supplied <paramref name="list"/> and applying necessary <paramref name="options"/>.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public virtual void Create (Stream file, IEnumerable<Entry> list, ResourceOptions options = null)
|
public virtual void Create (Stream file, IEnumerable<Entry> list, ResourceOptions options = null,
|
||||||
|
EntryCallback callback = null)
|
||||||
{
|
{
|
||||||
throw new NotImplementedException ("ArchiveFormat.Create is not implemented");
|
throw new NotImplementedException ("ArchiveFormat.Create is not implemented");
|
||||||
}
|
}
|
||||||
|
|
||||||
public virtual ResourceOptions GetOptions ()
|
public virtual ResourceOptions GetDefaultOptions ()
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public virtual ResourceOptions GetOptions (object widget)
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public virtual object GetCreationWidget ()
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public virtual object GetAccessWidget ()
|
||||||
{
|
{
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
@ -178,6 +202,11 @@ namespace GameRes
|
|||||||
/// Return value from ShowDialog()
|
/// Return value from ShowDialog()
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool InputResult { get; set; }
|
public bool InputResult { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Archive-specific options set by InputWidget.
|
||||||
|
/// </summary>
|
||||||
|
public ResourceOptions Options { get; set; }
|
||||||
}
|
}
|
||||||
|
|
||||||
public sealed class FormatCatalog
|
public sealed class FormatCatalog
|
||||||
|
Loading…
Reference in New Issue
Block a user