整理代码

This commit is contained in:
Chenx221 2024-10-17 12:25:14 +08:00
parent d3abca73ad
commit ade27ea87c
5 changed files with 72 additions and 193 deletions

View File

@ -1,8 +1,6 @@
using Microsoft.Data.Sqlite;
using System.Reflection;
using System.Reflection.Metadata;
using System.Text;
using System.Transactions;
namespace EscudeTools
{
@ -139,63 +137,18 @@ namespace EscudeTools
return sheet;
}
public bool ExportDatabase(int outputType, string? storePath)
public bool ExportDatabase(string? storePath)
{
if (db.Length == 0)
return false;
storePath ??= Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location) ?? throw new InvalidOperationException("Unable to determine the directory."); //导出位置
switch (outputType)
{
case 0: //sqlite
string targetFile = Path.Combine(storePath, dbName + ".db");
ExtractEmbeddedDatabase(targetFile);
return SqliteProcess(db, targetFile);
case 1: //csv
foreach (var s in db)
{
bool status = CsvProcess(s, Path.Combine(storePath, dbName + "_" + s.name + ".csv"));
if (!status)
{
throw new IOException($"Failed to export {s.name} CSV file.");
}
else
{
Console.WriteLine($"{s.name} CSV file exported successfully.");
}
}
return true;
default:
throw new NotSupportedException("Unsupported output type.");
}
}
private static void ExtractEmbeddedDatabase(string outputPath)
{
if (File.Exists(outputPath))
{
Console.WriteLine($"File {outputPath} already exists. Do you want to overwrite it? (y/n)");
string? input = Console.ReadLine();
if (input?.ToLower() != "y")
{
Console.WriteLine("Task cancelled, Exporting database aborted.");
return;
}
}
var assembly = Assembly.GetExecutingAssembly();
//foreach (var rn in assembly.GetManifestResourceNames())
//{
// Console.WriteLine(rn);
//}
string resourceName = "EscudeTools.empty.db";
using Stream stream = assembly.GetManifestResourceStream(resourceName) ?? throw new Exception($"Error, No resource with name {resourceName} found.");
using FileStream fileStream = new(outputPath, FileMode.Create, FileAccess.Write);
stream.CopyTo(fileStream);
string targetFile = Path.Combine(storePath, dbName + ".db");
Utils.ExtractEmbeddedDatabase(targetFile);
return SqliteProcess(db, targetFile);
}
private static bool SqliteProcess(Sheet[] db, string path)
{
//db含有多个sheet每个sheet中col存放标题对应数据库中应该是字段records存放数据对应数据库中应该是记录
using SqliteConnection connection = new($"Data Source={path};");
connection.Open();
using var transaction = connection.BeginTransaction();
@ -209,7 +162,7 @@ namespace EscudeTools
// Add columns to the create table query
foreach (var column in sheet.col)
{
createTableQuery.Append($"{column.name} {GetSQLiteColumnType(column.type)}, ");
createTableQuery.Append($"{column.name} {Utils.GetSQLiteColumnType(column.type)}, ");
}
createTableQuery.Remove(createTableQuery.Length - 2, 2); // Remove the last comma and space
@ -260,56 +213,5 @@ namespace EscudeTools
transaction.Commit();
return true;
}
private static string GetSQLiteColumnType(ushort type)
{
return type switch
{
// int
0x1 => "INTEGER",
// float
0x2 => "REAL",
// string
0x3 => "TEXT",
// bool
0x4 => "INTEGER",
_ => throw new NotSupportedException($"Unsupported column type: {type}"),
};
throw new NotImplementedException();
}
private static bool CsvProcess(Sheet s, string path)
{
if (string.IsNullOrEmpty(path))
throw new ArgumentException("File path cannot be null or empty.", nameof(path));
StringBuilder csvContent = new();
foreach (Column column in s.col)
{
csvContent.Append(column.name);
csvContent.Append(',');
}
csvContent.AppendLine();
foreach (Record record in s.records.values.Cast<Record>())
{
foreach (object value in record.values)
{
csvContent.Append(value);
csvContent.Append(',');
}
csvContent.AppendLine();
}
try
{
File.WriteAllText(path, csvContent.ToString());
return true;
}
catch (Exception ex)
{
Console.WriteLine($"Failed to export CSV file: {ex.Message}");
return false;
}
throw new NotImplementedException();
}
}
}

View File

@ -1,9 +1,4 @@
using static System.Runtime.InteropServices.JavaScript.JSType;
using System.Collections.Generic;
using System.Drawing;
using System.Xml.Linq;
using System.ComponentModel.Design;
//以下是垃圾代码,仅供参考
namespace EscudeTools
{
public static class Define

View File

@ -1,5 +1,4 @@
//这里的代码参考(Ctrl+C, Ctrl+V)了Garbro中关于ESCUDE BIN封包的实现
using System.Linq;
//这里的提取代码参考(Ctrl+C, Ctrl+V)了Garbro中关于ESCUDE BIN封包的实现
using System.Text;
namespace EscudeTools
@ -164,7 +163,7 @@ namespace EscudeTools
return true;
}
public bool Repack(string path, int version) //目前支持v2
public bool Repack(string path, int version) //目前支持v2v1
{
GeneratePItem(path);
m_seed = isLoaded ? LoadedKey : 2210579460;

View File

@ -1,7 +1,5 @@
using Microsoft.Data.Sqlite;
using System.Reflection;
using System.Text;
using System.Xml.Linq;
namespace EscudeTools
{
@ -77,10 +75,10 @@ namespace EscudeTools
byte[] head = br.ReadBytes(8);
if (!head.SequenceEqual(FileHeader))
return false;
sf.CodeSize = ReadUInt32(br);
sf.TextCount = ReadUInt32(br);
sf.TextSize = ReadUInt32(br);
sf.MessCount = ReadUInt32(br);
sf.CodeSize = Utils.ReadUInt32(br);
sf.TextCount = Utils.ReadUInt32(br);
sf.TextSize = Utils.ReadUInt32(br);
sf.MessCount = Utils.ReadUInt32(br);
if (sf.MessCount > 0)
if (sm == null)
if (!LoadScriptMess(Path.ChangeExtension(path, ".001")))
@ -99,7 +97,7 @@ namespace EscudeTools
sf.TextString = new string[sf.TextCount];
for (int i = 0; i < sf.TextCount; i++)
{
sf.TextString[i] = ReadStringFromTextData(sf.Text, (int)sf.TextOffset[i]);
sf.TextString[i] = Utils.ReadStringFromTextData(sf.Text, (int)sf.TextOffset[i]);
}
sf.Commands = [];
for (int i = 0; i < sf.CodeSize;)
@ -126,14 +124,6 @@ namespace EscudeTools
return true;
}
private static uint ReadUInt32(BinaryReader reader)
{
byte[] bytes = reader.ReadBytes(4);
if (bytes.Length < 4)
throw new EndOfStreamException("Unexpected end of stream while reading UInt32.");
return BitConverter.ToUInt32(bytes, 0);
}
private bool LoadScriptMess(string path)
{
if (!File.Exists(path))
@ -145,8 +135,8 @@ namespace EscudeTools
smEncrypted = head.SequenceEqual(MessHeader);
if (smEncrypted)
{
sm.Count = ReadUInt32(br);
sm.Size = ReadUInt32(br);
sm.Count = Utils.ReadUInt32(br);
sm.Size = Utils.ReadUInt32(br);
sm.Offset = [];
for (int i = 0; i < sm.Count; i++)
{
@ -169,7 +159,7 @@ namespace EscudeTools
uint offset = 0;
for (uint i = 0; i < sm.Size; i++)
{
if (ISKANJI(sm.Data[i]))
if (Utils.ISKANJI(sm.Data[i]))
i++;
else
{
@ -200,45 +190,21 @@ namespace EscudeTools
sm.DataString = new string[sm.Count];
for (int i = 0; i < sm.Count; i++)
{
sm.DataString[i] = ReadStringFromTextData(sm.Data, (int)sm.Offset[i]);
sm.DataString[i] = Utils.ReadStringFromTextData(sm.Data, (int)sm.Offset[i]);
}
return true;
}
private static bool ISKANJI(byte x)
{
return (((x) ^ 0x20) - 0xa1) <= 0x3b;
}
private static void ExtractEmbeddedDatabase(string outputPath)
{
if (File.Exists(outputPath))
{
Console.WriteLine($"File {outputPath} already exists. Do you want to overwrite it? (y/n)");
string? input = Console.ReadLine();
if (input?.ToLower() != "y")
{
Console.WriteLine("Task cancelled, Exporting database aborted.");
return;
}
}
var assembly = Assembly.GetExecutingAssembly();
string resourceName = "EscudeTools.empty.db";
using Stream stream = assembly.GetManifestResourceStream(resourceName) ?? throw new Exception($"Error, No resource with name {resourceName} found.");
using FileStream fileStream = new(outputPath, FileMode.Create, FileAccess.Write);
stream.CopyTo(fileStream);
}
public bool ExportDatabase(string? storePath)
{
if (sf.Code == null)
return false;
storePath ??= Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location) ?? throw new InvalidOperationException("Unable to determine the directory."); //导出位置
storePath ??= Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location) ?? throw new InvalidOperationException("Unable to determine the directory.");
if (string.IsNullOrEmpty(name))
return false;
string targetPath = Path.Combine(storePath, "script.db");
if (!File.Exists(targetPath))
ExtractEmbeddedDatabase(targetPath);
Utils.ExtractEmbeddedDatabase(targetPath);
return SqliteProcess(sf, targetPath);
}
@ -248,12 +214,12 @@ namespace EscudeTools
return false;
if (sm == null)
return true;
storePath ??= Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location) ?? throw new InvalidOperationException("Unable to determine the directory."); //导出位置
storePath ??= Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location) ?? throw new InvalidOperationException("Unable to determine the directory.");
if (string.IsNullOrEmpty(name))
return false;
string targetPath = Path.Combine(storePath, "script_sm.db");
if (!File.Exists(targetPath))
ExtractEmbeddedDatabase(targetPath);
Utils.ExtractEmbeddedDatabase(targetPath);
return SqliteProcess(sm, targetPath);
}
@ -303,7 +269,6 @@ namespace EscudeTools
return true;
}
private bool SqliteProcess(ScriptMessage sm, string path)
{
using SqliteConnection connection = new($"Data Source={path};");
@ -340,37 +305,5 @@ namespace EscudeTools
transaction.Commit();
return true;
}
private static string GetSQLiteColumnType(ushort type)
{
return type switch
{
// int
0x1 => "INTEGER",
// float
0x2 => "REAL",
// string
0x3 => "TEXT",
// bool
0x4 => "INTEGER",
_ => throw new NotSupportedException($"Unsupported column type: {type}"),
};
throw new NotImplementedException();
}
private static string ReadStringFromTextData(byte[] sheet_text, int offset)
{
List<byte> stringBytes = [];
for (int i = offset; i < sheet_text.Length && sheet_text[i] != 0x00; i++)
{
stringBytes.Add(sheet_text[i]);
}
EncodingProvider provider = CodePagesEncodingProvider.Instance;
Encoding? shiftJis = provider.GetEncoding("shift-jis");
return shiftJis == null
? throw new InvalidOperationException("Shift-JIS encoding not supported.")
: shiftJis.GetString(stringBytes.ToArray());
}
}
}

View File

@ -1,4 +1,5 @@
using System.Text;
using System.Reflection;
using System.Text;
namespace EscudeTools
{
@ -47,5 +48,54 @@ namespace EscudeTools
{
return (uint)(value[index] | value[index + 1] << 8 | value[index + 2] << 16 | value[index + 3] << 24);
}
public static uint ReadUInt32(BinaryReader reader)
{
byte[] bytes = reader.ReadBytes(4);
if (bytes.Length < 4)
throw new EndOfStreamException("Unexpected end of stream while reading UInt32.");
return BitConverter.ToUInt32(bytes, 0);
}
public static void ExtractEmbeddedDatabase(string outputPath)
{
if (File.Exists(outputPath))
{
Console.WriteLine($"File {outputPath} already exists. Do you want to overwrite it? (y/n)");
string? input = Console.ReadLine();
if (input?.ToLower() != "y")
{
Console.WriteLine("Task cancelled, Exporting database aborted.");
return;
}
}
var assembly = Assembly.GetExecutingAssembly();
string resourceName = "EscudeTools.empty.db";
using Stream stream = assembly.GetManifestResourceStream(resourceName) ?? throw new Exception($"Error, No resource with name {resourceName} found.");
using FileStream fileStream = new(outputPath, FileMode.Create, FileAccess.Write);
stream.CopyTo(fileStream);
}
public static string GetSQLiteColumnType(ushort type)
{
return type switch
{
// int
0x1 => "INTEGER",
// float
0x2 => "REAL",
// string
0x3 => "TEXT",
// bool
0x4 => "INTEGER",
_ => throw new NotSupportedException($"Unsupported column type: {type}"),
};
throw new NotImplementedException();
}
public static bool ISKANJI(byte x)
{
return (((x) ^ 0x20) - 0xa1) <= 0x3b;
}
}
}