-
-
Notifications
You must be signed in to change notification settings - Fork 427
/
Copy pathTexture.cs
92 lines (77 loc) · 3.42 KB
/
Texture.cs
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
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
using System;
using System.Runtime.InteropServices;
using Silk.NET.OpenGL;
using SixLabors.ImageSharp;
using SixLabors.ImageSharp.PixelFormats;
using SixLabors.ImageSharp.Processing;
namespace AndroidDemo
{
public class Texture : IDisposable
{
private uint _handle;
private GL _gl;
public unsafe Texture(GL gl, string path)
{
_gl = gl;
_handle = _gl.GenTexture();
Bind();
//Loading an image using imagesharp.
using (var img = Image.Load<Rgba32>(FileManager.OpenStream(path)))
{
//Reserve enough memory from the gpu for the whole image
gl.TexImage2D(TextureTarget.Texture2D, 0, InternalFormat.Rgba8, (uint) img.Width, (uint) img.Height, 0, PixelFormat.Rgba, PixelType.UnsignedByte, null);
img.ProcessPixelRows(accessor =>
{
//ImageSharp 2 does not store images in contiguous memory by default, so we must send the image row by row
for (int y = 0; y < accessor.Height; y++)
{
fixed (void* data = accessor.GetRowSpan(y))
{
//Loading the actual image.
gl.TexSubImage2D(TextureTarget.Texture2D, 0, 0, y, (uint) accessor.Width, 1, PixelFormat.Rgba, PixelType.UnsignedByte, data);
}
}
});
}
SetParameters();
}
public unsafe Texture(GL gl, Span<byte> data, uint width, uint height)
{
//Saving the gl instance.
_gl = gl;
//Generating the opengl handle;
_handle = _gl.GenTexture();
Bind();
//We want the ability to create a texture using data generated from code aswell.
fixed (void* d = &data[0])
{
//Setting the data of a texture.
_gl.TexImage2D(TextureTarget.Texture2D, 0, (int) InternalFormat.Rgba, width, height, 0, PixelFormat.Rgba, PixelType.UnsignedByte, d);
SetParameters();
}
}
private void SetParameters()
{
//Setting some texture perameters so the texture behaves as expected.
_gl.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureWrapS, (int) GLEnum.ClampToEdge);
_gl.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureWrapT, (int) GLEnum.ClampToEdge);
_gl.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMinFilter, (int) GLEnum.Linear);
_gl.TexParameter(TextureTarget.Texture2D, TextureParameterName.TextureMagFilter, (int) GLEnum.Linear);
//Generating mipmaps.
_gl.GenerateMipmap(TextureTarget.Texture2D);
}
public void Bind(TextureUnit textureSlot = TextureUnit.Texture0)
{
//When we bind a texture we can choose which textureslot we can bind it to.
_gl.ActiveTexture(textureSlot);
_gl.BindTexture(TextureTarget.Texture2D, _handle);
}
public void Dispose()
{
//In order to dispose we need to delete the opengl handle for the texure.
_gl.DeleteTexture(_handle);
}
}
}