From 487410e55f2e2de2de1a61fa378287d5625f7558 Mon Sep 17 00:00:00 2001 From: winscripter <142818255+winscripter@users.noreply.github.com> Date: Wed, 15 Jul 2026 20:30:58 +0400 Subject: [PATCH] Implement field encodings, move IJxlFields This is an implementation of field_encodings.h. Note that I avoided implementing EnumValid() and Values() functions, as we have dedicated methods in .NET to do exactly that (Enum.IsDefined, Enum.GetValues) --- .../Formats/Jxl/{IO => Fields}/IJxlFields.cs | 2 +- .../Formats/Jxl/Fields/JxlFieldExpressions.cs | 21 +++++++++++++++ .../Formats/Jxl/Fields/JxlU32Distribution.cs | 17 ++++++++++++ .../Formats/Jxl/Fields/JxlU32Enc.cs | 26 +++++++++++++++++++ 4 files changed, 65 insertions(+), 1 deletion(-) rename src/ImageSharp/Formats/Jxl/{IO => Fields}/IJxlFields.cs (90%) create mode 100644 src/ImageSharp/Formats/Jxl/Fields/JxlFieldExpressions.cs create mode 100644 src/ImageSharp/Formats/Jxl/Fields/JxlU32Distribution.cs create mode 100644 src/ImageSharp/Formats/Jxl/Fields/JxlU32Enc.cs diff --git a/src/ImageSharp/Formats/Jxl/IO/IJxlFields.cs b/src/ImageSharp/Formats/Jxl/Fields/IJxlFields.cs similarity index 90% rename from src/ImageSharp/Formats/Jxl/IO/IJxlFields.cs rename to src/ImageSharp/Formats/Jxl/Fields/IJxlFields.cs index 191cc96a3e..bdc09f5f41 100644 --- a/src/ImageSharp/Formats/Jxl/IO/IJxlFields.cs +++ b/src/ImageSharp/Formats/Jxl/Fields/IJxlFields.cs @@ -1,7 +1,7 @@ // Copyright (c) Six Labors. // Licensed under the Six Labors Split License. -namespace SixLabors.ImageSharp.Formats.Jxl.IO; +namespace SixLabors.ImageSharp.Formats.Jxl.Fields; /// /// Abstracts enumeration of all fields into a visitor. diff --git a/src/ImageSharp/Formats/Jxl/Fields/JxlFieldExpressions.cs b/src/ImageSharp/Formats/Jxl/Fields/JxlFieldExpressions.cs new file mode 100644 index 0000000000..8d74c81bb8 --- /dev/null +++ b/src/ImageSharp/Formats/Jxl/Fields/JxlFieldExpressions.cs @@ -0,0 +1,21 @@ +// Copyright (c) Six Labors. +// Licensed under the Six Labors Split License. + +namespace SixLabors.ImageSharp.Formats.Jxl.Fields; + +internal static class JxlFieldExpressions +{ + public static JxlU32Distribution Value(uint value) + { + const uint directConstant = JxlU32Distribution.DirectConstant; + + return new(value | directConstant); + } + + public static JxlU32Distribution BitsOffset(uint bits, uint offset) + => new(((bits - 1u) & 0x1Fu) + ((offset & 0x3FFFFFFu) << 5)); + + public static JxlU32Distribution Bits(uint value) => BitsOffset(value, 0u); + + public static int MakeBit(int index) => 1 << index; +} diff --git a/src/ImageSharp/Formats/Jxl/Fields/JxlU32Distribution.cs b/src/ImageSharp/Formats/Jxl/Fields/JxlU32Distribution.cs new file mode 100644 index 0000000000..355b6f533f --- /dev/null +++ b/src/ImageSharp/Formats/Jxl/Fields/JxlU32Distribution.cs @@ -0,0 +1,17 @@ +// Copyright (c) Six Labors. +// Licensed under the Six Labors Split License. + +namespace SixLabors.ImageSharp.Formats.Jxl.Fields; + +internal struct JxlU32Distribution(uint d) +{ + public const uint DirectConstant = 0x80000000u; + + public readonly bool IsDirect => (d & DirectConstant) != 0; + + public readonly uint Direct => d & (DirectConstant - 1u); + + public readonly uint ExtraBits => (d & 0x1Fu) + 1u; + + public readonly uint Offset => (d >> 5) & 0x3FFFFFF; +} diff --git a/src/ImageSharp/Formats/Jxl/Fields/JxlU32Enc.cs b/src/ImageSharp/Formats/Jxl/Fields/JxlU32Enc.cs new file mode 100644 index 0000000000..9583f57dac --- /dev/null +++ b/src/ImageSharp/Formats/Jxl/Fields/JxlU32Enc.cs @@ -0,0 +1,26 @@ +// Copyright (c) Six Labors. +// Licensed under the Six Labors Split License. + +using System.Diagnostics; + +namespace SixLabors.ImageSharp.Formats.Jxl.Fields; + +internal readonly struct JxlU32Enc +{ + private readonly InlineArray4 d = default; + + public JxlU32Enc(JxlU32Distribution d0, JxlU32Distribution d1, JxlU32Distribution d2, JxlU32Distribution d3) + { + this.d[0] = d0; + this.d[1] = d1; + this.d[2] = d2; + this.d[3] = d3; + } + + public JxlU32Distribution GetDistribution(int selector) + { + Debug.Assert(selector < 4, "Selector out of range"); + + return this.d[selector]; + } +}