Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .editorconfig
Original file line number Diff line number Diff line change
Expand Up @@ -131,7 +131,7 @@ csharp_style_throw_expression = true:warning
csharp_style_conditional_delegate_call = true:warning

### Code-block preferences
csharp_prefer_braces = when_multiline:warning
csharp_prefer_braces = when_multiline:suggestion
dotnet_diagnostic.SA1503.severity = warning # Doesn't follow above value
csharp_prefer_simple_using_statement = true:suggestion
csharp_style_prefer_tuple_swap = true:suggestion
Expand Down Expand Up @@ -216,6 +216,7 @@ dotnet_diagnostic.IDE1006.severity = warning
### .NET SDK
dotnet_diagnostic.CA1303.severity = none # We don't translate exception and log messages from English
dotnet_diagnostic.SA1025.severity = none # Allow spaces in comments to structure info
dotnet_diagnostic.IDE0019.severity = suggestion # Use pattern matching
dotnet_diagnostic.IDE0045.severity = suggestion # Simplify ifs
dotnet_diagnostic.IDE0046.severity = suggestion # Simplify ifs
dotnet_diagnostic.IDE0057.severity = suggestion # Slice can be simplified
Expand Down
21 changes: 18 additions & 3 deletions .github/workflows/build-and-release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,8 @@ on:
tags: [ "v*" ]

env:
DOTNET_VERSIONS: |
8.0.420
10.0.202
TEST_RESOURCES_NAME: 'resources-0.zip'
DOTNET_VERSIONS: 10.0.203
DOTNET_INSTALL_DIR: '/tmp/dotnet/'

jobs:
Expand All @@ -32,12 +31,28 @@ jobs:
with:
dotnet-version: ${{ env.DOTNET_VERSIONS }}

# Full test for master builds and PR of repo owners
- name: "Build, test, and bundle"
if: ${{ env.TEST_RESOURCES_URI != '' }}
run: >
dotnet run build.cs --
--target=Default
--target=Bundle
--dotnet-configuration=Release
--resource-uri=${{ env.TEST_RESOURCES_URI }}
--resource-name=${{ env.TEST_RESOURCES_NAME }}
--resource-usr=${{ env.TEST_RESOURCES_USR }}
--resource-pwd=${{ env.TEST_RESOURCES_PWD }}
env:
TEST_RESOURCES_URI: ${{ secrets.TEST_RESOURCES_URI }}
TEST_RESOURCES_USR: ${{ secrets.TEST_RESOURCES_USR }}
TEST_RESOURCES_PWD: ${{ secrets.TEST_RESOURCES_PWD }}

# Tests without resources for PR of external contributors
- name: "Build, test, and bundle"
if: ${{ env.TEST_RESOURCES_URI == '' }}
run: >
dotnet run build.cs -- --target=Default --target=Bundle --dotnet-configuration=Release

- name: "Publish artifacts to CI"
uses: actions/upload-artifact@v7
Expand Down
15 changes: 15 additions & 0 deletions .idea/.idea.JUSToolkit/.idea/.gitignore

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

8 changes: 8 additions & 0 deletions .idea/.idea.JUSToolkit/.idea/indexLayout.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

6 changes: 6 additions & 0 deletions .idea/.idea.JUSToolkit/.idea/vcs.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions JUSToolkit.sln.DotSettings
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
<wpf:ResourceDictionary xml:space="preserve" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:s="clr-namespace:System;assembly=mscorlib" xmlns:ss="urn:shemas-jetbrains-com:settings-storage-xaml" xmlns:wpf="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
<s:Boolean x:Key="/Default/UserDictionary/Words/=Koma/@EntryIndexedValue">True</s:Boolean></wpf:ResourceDictionary>
19 changes: 19 additions & 0 deletions JUSToolkit.slnx
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
<Solution>
<Configurations>
<Platform Name="Any CPU" />
<Platform Name="x64" />
<Platform Name="x86" />
</Configurations>
<Folder Name="/Build system/">
<File Path=".github\workflows\build-and-release.yml" />
<File Path="build.cs" />
<File Path="nuget.config" />
<File Path="src/Directory.Build.props" />
<File Path="src/Directory.Packages.props" />
<File Path="src/Tests.runsettings" />
</Folder>
<Project Path="src/JUS.CLI/JUS.CLI.csproj" />
<Project Path="src/JUS.SceneGatePlugin/JUS.SceneGatePlugin.csproj" />
<Project Path="src/JUS.Tests/JUS.Tests.csproj" />
<Project Path="src/JUS.Tool/JUS.Tool.csproj" />
</Solution>
14 changes: 5 additions & 9 deletions build.cs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#!/usr/bin/env dotnet run
#!/usr/bin/env dotnet run
#:property PublishAot=false
#:package Cake.Frosting.PleOps.Recipe@1.0.4-preview.33
#:package Cake.Frosting.PleOps.Recipe@1.0.4-preview.37

using System.Diagnostics.CodeAnalysis;
using Cake.Common.IO;
Expand Down Expand Up @@ -57,7 +57,7 @@ public override void Setup(BuildContext context, ISetupContext info)
new ProjectPublicationInfo(
"./src/JUS.CLI",
[ "win-x64", "linux-x64", "osx-x64" ],
"net8.0"));
"net10.0"));

context.ReadArguments();

Expand Down Expand Up @@ -108,11 +108,7 @@ public override bool ShouldRun(BuildContext context) =>

public override void Run(BuildContext context)
{
string resourcesPath = Path.GetFullPath(Path.Combine("resources", "tests"));
if (Directory.Exists(resourcesPath)) {
context.Log.Information("Test files already exists, skipping download.");
return;
}
string resourcesPath = Path.GetFullPath(Path.Combine("src", "JUS.Tests"));

string resourceUri = string.Format(context.TestResourceUri!, context.TestResourceName);
var downloadSettings = new DownloadFileSettings {
Expand All @@ -128,6 +124,6 @@ public override void Run(BuildContext context)
var compressedResources = context.DownloadFile(resourceUri, downloadSettings);

context.Log.Debug("Unzipping resource");
context.Unzip(compressedResources, resourcesPath);
context.Unzip(compressedResources, resourcesPath, true);
}
}
2 changes: 1 addition & 1 deletion nuget.config
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@

<packageSource key="SceneGate-Preview">
<package pattern="Texim*" />
<package pattern="Yarhl*" />
<!-- <package pattern="Yarhl*" />-->
<package pattern="SceneGate.*" />
</packageSource>

Expand Down
41 changes: 19 additions & 22 deletions src/Directory.Packages.props
Original file line number Diff line number Diff line change
@@ -1,24 +1,21 @@
<Project>
<!-- Centralize dependency management -->
<ItemGroup>
<PackageVersion Include="Yarhl" Version="4.0.1-preview.43" />
<PackageVersion Include="Yarhl.Media.Text" Version="4.0.1-preview.43" />
<PackageVersion Include="Texim" Version="0.1.0-preview.320" />
<PackageVersion Include="Texim.Games" Version="0.1.0-preview.320" />
<PackageVersion Include="SceneGate.Ekona" Version="1.1.1-preview.87" />

<PackageVersion Include="coverlet.collector" Version="6.0.4" />
<PackageVersion Include="FluentAssertions" Version="7.2.1" />
<PackageVersion Include="nunit" Version="4.4.0" />
<PackageVersion Include="NUnit3TestAdapter" Version="6.1.0" />
<PackageVersion Include="NUnit.Analyzers" Version="4.11.2" />
<PackageVersion Include="Microsoft.NET.Test.Sdk" Version="18.0.1"/>
<PackageVersion Include="YamlDotNet" Version="16.3.0" />

<PackageVersion Include="System.CommandLine" Version="2.0.3" />

<PackageVersion Include="Microsoft.SourceLink.GitHub" Version="10.0.102" />

<PackageVersion Include="SonarAnalyzer.CSharp" Version="10.20.0.135146" />
</ItemGroup>
<!-- Centralize dependency management -->
<ItemGroup>
<PackageVersion Include="SceneGate.UI.Formats" Version="0.1.1-preview.17" />
<PackageVersion Include="Yarhl" Version="4.1.0" />
<PackageVersion Include="Yarhl.Media.Text" Version="4.1.0" />
<PackageVersion Include="Texim" Version="0.1.0-preview.321" />
<PackageVersion Include="Texim.Games" Version="0.1.0-preview.321" />
<PackageVersion Include="SceneGate.Ekona" Version="1.1.1-preview.87" />
<PackageVersion Include="coverlet.collector" Version="10.0.0" />
<PackageVersion Include="FluentAssertions" Version="7.2.1" />
<PackageVersion Include="nunit" Version="4.5.1" />
<PackageVersion Include="NUnit3TestAdapter" Version="6.2.0" />
<PackageVersion Include="NUnit.Analyzers" Version="4.12.0" />
<PackageVersion Include="Microsoft.NET.Test.Sdk" Version="18.4.0" />
<PackageVersion Include="YamlDotNet" Version="17.0.1" />
<PackageVersion Include="System.CommandLine" Version="2.0.6" />
<PackageVersion Include="Microsoft.SourceLink.GitHub" Version="10.0.202" />
<PackageVersion Include="SonarAnalyzer.CSharp" Version="10.23.0.137933" />
</ItemGroup>
</Project>
2 changes: 1 addition & 1 deletion src/JUS.CLI/JUS.CLI.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
<PropertyGroup>
<OutputType>Exe</OutputType>

<TargetFramework>net8.0</TargetFramework>
<TargetFramework>net10.0</TargetFramework>
</PropertyGroup>

<ItemGroup>
Expand Down
21 changes: 21 additions & 0 deletions src/JUS.SceneGatePlugin/JUS.SceneGatePlugin.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<Description>SceneGate UI plugin for the JUS game formats.</Description>

<TargetFramework>net10.0</TargetFramework>

<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
<GenerateDocumentationFile>false</GenerateDocumentationFile>
</PropertyGroup>

<ItemGroup>
<PackageReference Include="SceneGate.UI.Formats"/>
</ItemGroup>

<ItemGroup>
<ProjectReference Include="..\JUS.Tool\JUS.Tool.csproj"/>
</ItemGroup>

</Project>
88 changes: 88 additions & 0 deletions src/JUS.SceneGatePlugin/JusBinaryHeaderConverterMatcher.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
using System.Diagnostics.CodeAnalysis;
using JUS.Tool.Containers.Converters;
using JUS.Tool.Graphics.Converters;
using SceneGate.UI.Formats.Discovery;
using Yarhl.FileSystem;
using Yarhl.IO;

namespace JUS.SceneGatePlugin;

[DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicConstructors)]
public sealed class JusBinaryHeaderConverterMatcher : IConverterMatcher
{
private static readonly HeaderFormat[] SupportedFormats = [
// Containers
HeaderFormat.Create<Binary2Alar2>("ALAR", 2, null),
HeaderFormat.Create<Binary2Alar3>("ALAR", 3, null),
// Graphics
HeaderFormat.Create<Binary2Almt>("ALMT", null, null),
HeaderFormat.Create<Binary2Dig>("DSIG", null, null),
HeaderFormat.Create<BinaryToDtx3>("DSTX", 1, 3),
HeaderFormat.Create<BinaryDtx4ToSpriteImage>("DSTX", 1, 4),
];

public ConverterMatcherResult Match(Node input, ConverterMatcherContext context)
{
if (input.Format is not IBinary) {
return ConverterMatcherResult.Incompatible();
}

// Validate the header data
HeaderFormat? compatibleFormat = SupportedFormats
.FirstOrDefault(f => MatchFormat(context, f));
if (compatibleFormat is null) {
return ConverterMatcherResult.Incompatible();
}

// header data match... validate this is a supported game
bool? compatibleSoftware = SupportedSoftware.IsFromCompatibleSoftware(input, out _);
if (compatibleSoftware == false) {
return ConverterMatcherResult.Incompatible();
}

// "should be" if header match, but we can't verify the game code
MatchingConfidence level = compatibleSoftware == true ? MatchingConfidence.Confident : MatchingConfidence.ShouldBe;
object converter = compatibleFormat.ConverterFactory();
return new ConverterMatcherResult(level, compatibleFormat.ConverterType, converter);
}

private static bool MatchFormat(ConverterMatcherContext context, HeaderFormat format)
{
int requiredHeaderData = format switch {
{ Flags: not null } => 6,
{ Version: not null } => 5,
_ => 4
};
if (context.Header.Length < requiredHeaderData) {
return false;
}

if (context.Header.ReadAsciiString(0, 4) != format.Id) {
return false;
}

if (format.Version.HasValue && context.Header.Span[4] != format.Version.Value) {
return false;
}

if (format.Flags.HasValue && context.Header.Span[5] != format.Flags.Value) {
return false;
}

return true;
}

private sealed record HeaderFormat(
string Id,
byte? Version,
byte? Flags,
Type ConverterType,
Func<object> ConverterFactory)
{
public static HeaderFormat Create<T>(string id, byte? version, byte? flags)
where T : class, new()
{
return new HeaderFormat(id, version, flags, typeof(T), () => new T());
}
}
}
Loading
Loading