Gltf и json. Декодирование строки буфера

Существуют два простых метода для декодирования строки base64 (в С#). Хочу собрать json для формирования gltf, и закодировать свои координаты и позиции вершин в буфер. Для этого пытаюсь понять, как оно устроено по умолчанию. В туториале разбирается примитивный треугольник - 3 координаты. Чтобы создать свою строку Base64, нужно понять как она получена для этого примитива. Попытался декодировать, тщетно. Вопрос - как получается строка в свойстве uri:

"buffers" : [
    {
      "uri" : "data:application/octet-stream;base64,AAABAAIAAAAAAAAAAAAAAAAAAAAAAIA/AAAAAAAAAAAAAAAAAACAPwAAAAA=",
      "byteLength" : 44
    }
  ],

Ответы (1 шт):

Автор решения: aepot

Если раскодировать base64 и эвристически глянуть на этот массив в HEX формате, по можно увидеть следующее:

00000100020000000000000000000000000000000000803F0000000000000000000000000000803F00000000

Здесь внимание привлекают комбинации 0000803F так как это 1 в формате float. Если представить, что в конце массива 3 трехмерных вектора, то тогда их можно раскодировать. А вот что представляют собой первые 8 байт массива - загадка. Без знаний, что именно там лежит и не заглядывая в спецификацию хранения данных - расшифровать это проблематично.

Вот код для начала

class Program
{
    static void Main(string[] args)
    {
        string json = """
{
  "buffers" : [
    {
      "uri" : "data:application/octet-stream;base64,AAABAAIAAAAAAAAAAAAAAAAAAAAAAIA/AAAAAAAAAAAAAAAAAACAPwAAAAA=",
      "byteLength" : 44
    }
  ],
}
""";
        MyBuffer[] buffers = JsonSerializer.Deserialize<MyData>(json, new JsonSerializerOptions { AllowTrailingCommas = true }).Buffers;
        MyBuffer buffer = buffers[0];
        string uri = buffer.Uri;
        const string prefix = "data:application/octet-stream;base64,";
        if (uri.StartsWith(prefix))
        {
            string base64 = uri.Substring(prefix.Length);
            byte[] bytes = Convert.FromBase64String(base64);
            Console.WriteLine(Convert.ToHexString(bytes));
            Console.WriteLine(Convert.ToHexString(bytes[..8]));
            Vector3[] vertices = MemoryMarshal.Cast<byte, Vector3>(bytes[8..]).ToArray();
            Console.WriteLine(string.Join(Environment.NewLine, vertices));
        }
    }
}

public class MyData
{
    [JsonPropertyName("buffers")]
    public MyBuffer[] Buffers {  get; set; }
}

public class MyBuffer
{
    [JsonPropertyName("uri")]
    public string Uri { get; set; }

    [JsonPropertyName("byteLength")]
    public int ByteLength {  get; set; } 
}

Вот вывод в консоль

00000100020000000000000000000000000000000000803F0000000000000000000000000000803F00000000
0000010002000000
<0  0  0>
<1  0  0>
<0  1  0>

Но я бы начал с изучания glTF спецификации. Наверное в ней и хранится ответ на вопрос, что же там за числа и в каком формате лежат данные в первых 8 байтах массива.

→ Ссылка