1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
|
using System.Buffers.Binary;
using System.IO.Compression;
using Raylib_cs;
namespace OnekoOnline;
class Bitmap : IDisposable
{
public readonly int Width;
public readonly int Height;
public readonly Texture2D Texture;
readonly byte[] SerializedData;
public Bitmap(Image img)
{
Width = img.Width;
Height = img.Height;
Texture = Raylib.LoadTextureFromImage(img);
//Get Data for Serialization
Color[] colors = new Color[Width*Height];
int i = 0;
for (int x = 0; x < Width; x++) {
for (int y = 0; y < Height; y++) {
colors[i] = Raylib.GetImageColor(img, x, y);
i++;
}
}
byte[] data = new byte[(colors.Length*4) + (sizeof(short)*2)];
BinaryPrimitives.WriteInt16LittleEndian(data.AsSpan(0, sizeof(short)), (short)Width);
BinaryPrimitives.WriteInt16LittleEndian(data.AsSpan(sizeof(short), sizeof(short)), (short)Height);
int position = sizeof(short)*2;
for (int c = 0; c < colors.Length; c++) {
data[position] = colors[c].R;
data[position+1] = colors[c].G;
data[position+2] = colors[c].B;
data[position+3] = colors[c].A;
position += 4;
}
using MemoryStream stream = new();
using DeflateStream compressor = new(stream, CompressionLevel.Optimal);
compressor.Write(data);
compressor.Close();
SerializedData = stream.ToArray();
Raylib.UnloadImage(img);
}
Bitmap(Image img, byte[] serializedData)
{
Width = img.Width;
Height = img.Height;
SerializedData = serializedData;
Texture = Raylib.LoadTextureFromImage(img);
Raylib.UnloadImage(img);
}
public static Bitmap FromFile(string path)
{
if (!File.Exists(path) || new FileInfo(path).Length > 40000 || !path.Contains(".png"))
return new Bitmap(Raylib.GenImageChecked(32, 32, 4, 4, Color.BLACK, Color.PINK));
byte[] memory = File.ReadAllBytes(path);
return FromPNGMemory(memory);
}
public static Bitmap FromPNGMemory(byte[] memory)
{
return new Bitmap(Raylib.LoadImageFromMemory(".png", memory));
}
public static Bitmap Deserialize(ReadOnlySpan<byte> span)
{
byte[] compressed = span.ToArray();
byte[] data;
{
using MemoryStream input = new(compressed);
using MemoryStream output = new();
using DeflateStream decompressor = new(input, CompressionMode.Decompress);
decompressor.CopyTo(output);
data = output.ToArray();
}
int width = BinaryPrimitives.ReadInt16LittleEndian(data.AsSpan(0, sizeof(short)));
int height = BinaryPrimitives.ReadInt16LittleEndian(data.AsSpan(sizeof(short), sizeof(short)));
Image img = Raylib.GenImageChecked(width, height, 4, 4, Color.PINK, Color.BLACK);
int i = sizeof(short)*2;
for (int x = 0; x < width; x++) {
for (int y = 0; y < height; y++) {
Color color = new(data[i], data[i+1], data[i+2], data[i+3]);
Raylib.ImageDrawPixel(ref img, x, y, color);
i += 4;
}
}
return new Bitmap(img, compressed);
}
public byte[] Serialize()
{
return SerializedData;
}
public void Dispose()
{
Raylib.UnloadTexture(Texture);
}
}
|